From 61a4b50c01ad148212eab9fcb3fee7bf506273ea Mon Sep 17 00:00:00 2001 From: Paul Buschmann Date: Sun, 15 Jun 2025 20:14:25 +0200 Subject: [PATCH 01/22] chore: force LF on windows --- .gitattributes | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.gitattributes b/.gitattributes index 873ddfb587..666eddc88d 100644 --- a/.gitattributes +++ b/.gitattributes @@ -1,3 +1,5 @@ +* text=auto eol=lf + *.ml linguist-language=OCaml *.mli linguist-language=OCaml *.res linguist-language=ReScript From 475f49dbe31177e99d9fedd433f7b44a56261a6e Mon Sep 17 00:00:00 2001 From: Paul Buschmann Date: Sun, 15 Jun 2025 21:14:43 +0200 Subject: [PATCH 02/22] feat: upstream changes of rescript-lang/rewatch#162 --- rewatch/src/build.rs | 17 ++++ rewatch/src/build/clean.rs | 6 +- rewatch/src/cli.rs | 178 +++++++++++++++++++++++++++++++++++ rewatch/src/helpers.rs | 35 +++++++ rewatch/src/lib.rs | 1 + rewatch/src/main.rs | 187 ++++++++++++++----------------------- rewatch/tests/compile.sh | 16 ++-- rewatch/tests/utils.sh | 4 +- 8 files changed, 315 insertions(+), 129 deletions(-) create mode 100644 rewatch/src/cli.rs diff --git a/rewatch/src/build.rs b/rewatch/src/build.rs index c76120064e..ab00db8aad 100644 --- a/rewatch/src/build.rs +++ b/rewatch/src/build.rs @@ -18,10 +18,12 @@ use console::style; use indicatif::{ProgressBar, ProgressStyle}; use log::log_enabled; use serde::Serialize; +use std::ffi::OsString; use std::fmt; use std::fs::File; use std::io::{stdout, Write}; use std::path::{Path, PathBuf}; +use std::process::Stdio; use std::time::{Duration, Instant}; use self::compile::compiler_args; @@ -551,3 +553,18 @@ pub fn build( } } } + +pub fn pass_through_legacy(args: Vec) -> i32 { + let project_root = helpers::get_abs_path(Path::new(".")); + let workspace_root = helpers::get_workspace_root(&project_root); + + let bsb_path = helpers::get_rescript_legacy(&project_root, workspace_root); + + let status = std::process::Command::new(bsb_path) + .args(args) + .stdout(Stdio::inherit()) + .stderr(Stdio::inherit()) + .status(); + + status.map(|s| s.code().unwrap_or(1)).unwrap_or(1) +} diff --git a/rewatch/src/build/clean.rs b/rewatch/src/build/clean.rs index 5624e6ac33..0057437997 100644 --- a/rewatch/src/build/clean.rs +++ b/rewatch/src/build/clean.rs @@ -335,7 +335,6 @@ pub fn clean( path: &Path, show_progress: bool, bsc_path: &Option, - build_dev_deps: bool, snapshot_output: bool, ) -> Result<()> { let project_root = helpers::get_abs_path(path); @@ -345,8 +344,9 @@ pub fn clean( &project_root, &workspace_root, show_progress, - // Always clean dev dependencies - build_dev_deps, + // Build the package tree with dev dependencies. + // They should always be cleaned if they are there. + true, )?; let root_config_name = packages::read_package_name(&project_root)?; let bsc_path = match bsc_path { diff --git a/rewatch/src/cli.rs b/rewatch/src/cli.rs new file mode 100644 index 0000000000..87ec1efb09 --- /dev/null +++ b/rewatch/src/cli.rs @@ -0,0 +1,178 @@ +use std::ffi::OsString; + +use clap::{Args, Parser, Subcommand}; +use clap_verbosity_flag::InfoLevel; + +/// Rewatch is an alternative build system for the Rescript Compiler bsb (which uses Ninja internally). It strives +/// to deliver consistent and faster builds in monorepo setups with multiple packages, where the +/// default build system fails to pick up changed interfaces across multiple packages. +#[derive(Parser, Debug)] +#[command(version)] +#[command(args_conflicts_with_subcommands = true)] +pub struct Cli { + /// Verbosity: + /// -v -> Debug + /// -vv -> Trace + /// -q -> Warn + /// -qq -> Error + /// -qqq -> Off. + /// Default (/ no argument given): 'info' + #[command(flatten)] + pub verbose: clap_verbosity_flag::Verbosity, + + /// The command to run. If not provided it will default to build. + #[command(subcommand)] + pub command: Option, + + /// The relative path to where the main rescript.json resides. IE - the root of your project. + #[arg(default_value = ".")] + pub folder: String, + + #[command(flatten)] + pub build_args: BuildArgs, +} + +#[derive(Args, Debug, Clone)] +pub struct BuildArgs { + /// Filter files by regex + /// + /// Filter allows for a regex to be supplied which will filter the files to be compiled. For + /// instance, to filter out test files for compilation while doing feature work. + #[arg(short, long)] + pub filter: Option, + + /// Action after build + /// + /// This allows one to pass an additional command to the watcher, which allows it to run when + /// finished. For instance, to play a sound when done compiling, or to run a test suite. + /// NOTE - You may need to add '--color=always' to your subcommand in case you want to output + /// color as well + #[arg(short, long)] + pub after_build: Option, + + /// Create source_dirs.json + /// + /// This creates a source_dirs.json file at the root of the monorepo, which is needed when you + /// want to use Reanalyze + #[arg(short, long, default_value_t = false, num_args = 0..=1)] + pub create_sourcedirs: bool, + + /// Build development dependencies + /// + /// This is the flag to also compile development dependencies + /// It's important to know that we currently do not discern between project src, and + /// dependencies. So enabling this flag will enable building _all_ development dependencies of + /// _all_ packages + #[arg(long, default_value_t = false, num_args = 0..=1)] + pub dev: bool, + + /// Disable timing on the output + #[arg(short, long, default_value_t = false, num_args = 0..=1)] + pub no_timing: bool, + + /// simple output for snapshot testing + #[arg(short, long, default_value = "false", num_args = 0..=1)] + pub snapshot_output: bool, + + /// Path to bsc + #[arg(long)] + pub bsc_path: Option, +} + +#[derive(Args, Clone, Debug)] +pub struct WatchArgs { + /// Filter files by regex + /// + /// Filter allows for a regex to be supplied which will filter the files to be compiled. For + /// instance, to filter out test files for compilation while doing feature work. + #[arg(short, long)] + pub filter: Option, + + /// Action after build + /// + /// This allows one to pass an additional command to the watcher, which allows it to run when + /// finished. For instance, to play a sound when done compiling, or to run a test suite. + /// NOTE - You may need to add '--color=always' to your subcommand in case you want to output + /// color as well + #[arg(short, long)] + pub after_build: Option, + + /// Create source_dirs.json + /// + /// This creates a source_dirs.json file at the root of the monorepo, which is needed when you + /// want to use Reanalyze + #[arg(short, long, default_value_t = false, num_args = 0..=1)] + pub create_sourcedirs: bool, + + /// Build development dependencies + /// + /// This is the flag to also compile development dependencies + /// It's important to know that we currently do not discern between project src, and + /// dependencies. So enabling this flag will enable building _all_ development dependencies of + /// _all_ packages + #[arg(long, default_value_t = false, num_args = 0..=1)] + pub dev: bool, + + /// simple output for snapshot testing + #[arg(short, long, default_value = "false", num_args = 0..=1)] + pub snapshot_output: bool, + + /// Path to bsc + #[arg(long)] + pub bsc_path: Option, +} + +#[derive(Subcommand, Clone, Debug)] +pub enum Command { + /// Build using Rewatch + Build(BuildArgs), + /// Build, then start a watcher + Watch(WatchArgs), + /// Clean the build artifacts + Clean { + /// Path to bsc + #[arg(long)] + bsc_path: Option, + + /// simple output for snapshot testing + #[arg(short, long, default_value = "false", num_args = 0..=1)] + snapshot_output: bool, + }, + /// Alias to `legacy format`. + #[command(disable_help_flag = true)] + Format { + #[arg(allow_hyphen_values = true, num_args = 0..)] + format_args: Vec, + }, + /// Alias to `legacy dump`. + #[command(disable_help_flag = true)] + Dump { + #[arg(allow_hyphen_values = true, num_args = 0..)] + dump_args: Vec, + }, + /// This prints the compiler arguments. It expects the path to a rescript.json file. + CompilerArgs { + /// Path to a rescript.json file + #[command()] + path: String, + + #[arg(long, default_value_t = false, num_args = 0..=1)] + dev: bool, + + /// To be used in conjunction with compiler_args + #[arg(long)] + rescript_version: Option, + + /// A custom path to bsc + #[arg(long)] + bsc_path: Option, + }, + /// Use the legacy build system. + /// + /// After this command is encountered, the rest of the arguments are passed to the legacy build system. + #[command(disable_help_flag = true)] + Legacy { + #[arg(allow_hyphen_values = true, num_args = 0..)] + legacy_args: Vec, + }, +} diff --git a/rewatch/src/helpers.rs b/rewatch/src/helpers.rs index a91dee77f5..b05dc9b2ad 100644 --- a/rewatch/src/helpers.rs +++ b/rewatch/src/helpers.rs @@ -218,6 +218,41 @@ pub fn get_bsc(root_path: &Path, workspace_root: &Option) -> PathBuf { } } +pub fn get_rescript_legacy(root_path: &Path, workspace_root: Option) -> PathBuf { + let subfolder = match (std::env::consts::OS, std::env::consts::ARCH) { + ("macos", "aarch64") => "darwin-arm64", + ("macos", _) => "darwin-x64", + ("linux", "aarch64") => "linux-arm64", + ("linux", _) => "linux-x64", + ("windows", "aarch64") => "win-arm64", + ("windows", _) => "win-x64", + _ => panic!("Unsupported architecture"), + }; + + let legacy_path_fragment = Path::new("node_modules") + .join("@rescript") + .join(subfolder) + .join("bin") + .join("rescript-legacy"); + + match ( + root_path + .join(&legacy_path_fragment) + .canonicalize() + .map(StrippedVerbatimPath::to_stripped_verbatim_path), + workspace_root.map(|workspace_root| { + workspace_root + .join(&legacy_path_fragment) + .canonicalize() + .map(StrippedVerbatimPath::to_stripped_verbatim_path) + }), + ) { + (Ok(path), _) => path, + (_, Some(Ok(path))) => path, + _ => panic!("Could not find rescript-legacy"), + } +} + pub fn string_ends_with_any(s: &Path, suffixes: &[&str]) -> bool { suffixes .iter() diff --git a/rewatch/src/lib.rs b/rewatch/src/lib.rs index 9dc6f5591c..2df92a48f3 100644 --- a/rewatch/src/lib.rs +++ b/rewatch/src/lib.rs @@ -1,4 +1,5 @@ pub mod build; +pub mod cli; pub mod cmd; pub mod config; pub mod helpers; diff --git a/rewatch/src/main.rs b/rewatch/src/main.rs index 5c27a4d02b..dcebec5945 100644 --- a/rewatch/src/main.rs +++ b/rewatch/src/main.rs @@ -1,93 +1,17 @@ use anyhow::Result; -use clap::{Parser, ValueEnum}; -use clap_verbosity_flag::InfoLevel; +use clap::Parser; use log::LevelFilter; use regex::Regex; -use std::io::Write; -use std::path::{Path, PathBuf}; +use std::{ + io::Write, + path::{Path, PathBuf}, +}; -use rewatch::{build, cmd, lock, watcher}; - -#[derive(Debug, Clone, ValueEnum)] -enum Command { - /// Build using Rewatch - Build, - /// Build, then start a watcher - Watch, - /// Clean the build artifacts - Clean, -} - -/// Rewatch is an alternative build system for the Rescript Compiler bsb (which uses Ninja internally). It strives -/// to deliver consistent and faster builds in monorepo setups with multiple packages, where the -/// default build system fails to pick up changed interfaces across multiple packages. -#[derive(Parser, Debug)] -#[command(version)] -struct Args { - #[arg(value_enum)] - command: Option, - - /// The relative path to where the main rescript.json resides. IE - the root of your project. - folder: Option, - - /// Filter allows for a regex to be supplied which will filter the files to be compiled. For - /// instance, to filter out test files for compilation while doing feature work. - #[arg(short, long)] - filter: Option, - - /// This allows one to pass an additional command to the watcher, which allows it to run when - /// finished. For instance, to play a sound when done compiling, or to run a test suite. - /// NOTE - You may need to add '--color=always' to your subcommand in case you want to output - /// colour as well - #[arg(short, long)] - after_build: Option, - - // Disable timing on the output - #[arg(short, long, default_value = "false", num_args = 0..=1)] - no_timing: bool, - - // simple output for snapshot testing - #[arg(short, long, default_value = "false", num_args = 0..=1)] - snapshot_output: bool, - - /// Verbosity: - /// -v -> Debug - /// -vv -> Trace - /// -q -> Warn - /// -qq -> Error - /// -qqq -> Off. - /// Default (/ no argument given): 'info' - #[command(flatten)] - verbose: clap_verbosity_flag::Verbosity, - - /// This creates a source_dirs.json file at the root of the monorepo, which is needed when you - /// want to use Reanalyze - #[arg(short, long, default_value_t = false, num_args = 0..=1)] - create_sourcedirs: bool, - - /// This prints the compiler arguments. It expects the path to a rescript.json file. - /// This also requires --bsc-path and --rescript-version to be present - #[arg(long)] - compiler_args: Option, - - /// This is the flag to also compile development dependencies - /// It's important to know that we currently do not discern between project src, and - /// dependencies. So enabling this flag will enable building _all_ development dependencies of - /// _all_ packages - #[arg(long, default_value_t = false, num_args = 0..=1)] - dev: bool, - - /// To be used in conjunction with compiler_args - #[arg(long)] - rescript_version: Option, - - /// A custom path to bsc - #[arg(long)] - bsc_path: Option, -} +use rewatch::{build, cli, cmd, lock, watcher}; fn main() -> Result<()> { - let args = Args::parse(); + let args = cli::Cli::parse(); + let log_level_filter = args.verbose.log_level_filter(); env_logger::Builder::new() @@ -96,82 +20,113 @@ fn main() -> Result<()> { .target(env_logger::fmt::Target::Stdout) .init(); - let command = args.command.unwrap_or(Command::Build); - let folder = args.folder.unwrap_or(".".to_string()); - let filter = args - .filter - .map(|filter| Regex::new(filter.as_ref()).expect("Could not parse regex")); + let command = args.command.unwrap_or(cli::Command::Build(args.build_args)); - match args.compiler_args { - None => (), - Some(path) => { + // handle those commands early, because we don't need a lock for them + match command.clone() { + cli::Command::Legacy { legacy_args } => { + let code = build::pass_through_legacy(legacy_args); + std::process::exit(code); + } + cli::Command::Format { mut format_args } => { + format_args.insert(0, "format".into()); + let code = build::pass_through_legacy(format_args); + std::process::exit(code); + } + cli::Command::Dump { mut dump_args } => { + dump_args.insert(0, "dump".into()); + let code = build::pass_through_legacy(dump_args); + std::process::exit(code); + } + cli::Command::CompilerArgs { + path, + dev, + rescript_version, + bsc_path, + } => { println!( "{}", build::get_compiler_args( Path::new(&path), - args.rescript_version, - &args.bsc_path.map(PathBuf::from), - args.dev + rescript_version, + &bsc_path.map(PathBuf::from), + dev )? ); std::process::exit(0); } + _ => (), } // The 'normal run' mode will show the 'pretty' formatted progress. But if we turn off the log // level, we should never show that. let show_progress = log_level_filter == LevelFilter::Info; - match lock::get(&folder) { + match lock::get(&args.folder) { lock::Lock::Error(ref e) => { println!("Could not start Rewatch: {e}"); std::process::exit(1) } lock::Lock::Aquired(_) => match command { - Command::Clean => build::clean::clean( - Path::new(&folder), + cli::Command::Clean { + bsc_path, + snapshot_output, + } => build::clean::clean( + Path::new(&args.folder), show_progress, - &args.bsc_path.map(PathBuf::from), - args.dev, - args.snapshot_output, + &bsc_path.map(PathBuf::from), + snapshot_output, ), - Command::Build => { + cli::Command::Build(build_args) => { + let filter = build_args + .filter + .map(|filter| Regex::new(filter.as_ref()).expect("Could not parse regex")); + match build::build( &filter, - Path::new(&folder), + Path::new(&args.folder), show_progress, - args.no_timing, - args.create_sourcedirs, - &args.bsc_path.map(PathBuf::from), - args.dev, - args.snapshot_output, + build_args.no_timing, + build_args.create_sourcedirs, + &build_args.bsc_path.map(PathBuf::from), + build_args.dev, + build_args.snapshot_output, ) { Err(e) => { println!("{e}"); std::process::exit(1) } Ok(_) => { - if let Some(args_after_build) = args.after_build { + if let Some(args_after_build) = build_args.after_build { cmd::run(args_after_build) } std::process::exit(0) } }; } - Command::Watch => { + cli::Command::Watch(watch_args) => { + let filter = watch_args + .filter + .map(|filter| Regex::new(filter.as_ref()).expect("Could not parse regex")); watcher::start( &filter, show_progress, - &folder, - args.after_build, - args.create_sourcedirs, - args.dev, - args.bsc_path, - args.snapshot_output, + &args.folder, + watch_args.after_build, + watch_args.create_sourcedirs, + watch_args.dev, + watch_args.bsc_path, + watch_args.snapshot_output, ); Ok(()) } + cli::Command::CompilerArgs { .. } + | cli::Command::Legacy { .. } + | cli::Command::Format { .. } + | cli::Command::Dump { .. } => { + unreachable!("command already handled") + } }, } } diff --git a/rewatch/tests/compile.sh b/rewatch/tests/compile.sh index fd035bf902..9fc6ebb4bc 100755 --- a/rewatch/tests/compile.sh +++ b/rewatch/tests/compile.sh @@ -33,32 +33,32 @@ fi node ./packages/main/src/Main.mjs > ./packages/main/src/output.txt mv ./packages/main/src/Main.res ./packages/main/src/Main2.res -rewatch build &> ../tests/snapshots/rename-file.txt +rewatch build --no-timing --snapshot-output &> ../tests/snapshots/rename-file.txt mv ./packages/main/src/Main2.res ./packages/main/src/Main.res # Rename a file with a dependent - this should trigger an error mv ./packages/main/src/InternalDep.res ./packages/main/src/InternalDep2.res -rewatch build &> ../tests/snapshots/rename-file-internal-dep.txt +rewatch build --no-timing --snapshot-output &> ../tests/snapshots/rename-file-internal-dep.txt # normalize paths so the snapshot is the same on all machines normalize_paths ../tests/snapshots/rename-file-internal-dep.txt mv ./packages/main/src/InternalDep2.res ./packages/main/src/InternalDep.res # Rename a file with a dependent in a namespaced package - this should trigger an error (regression) mv ./packages/new-namespace/src/Other_module.res ./packages/new-namespace/src/Other_module2.res -rewatch build &> ../tests/snapshots/rename-file-internal-dep-namespace.txt +rewatch build --no-timing --snapshot-output &> ../tests/snapshots/rename-file-internal-dep-namespace.txt # normalize paths so the snapshot is the same on all machines normalize_paths ../tests/snapshots/rename-file-internal-dep-namespace.txt mv ./packages/new-namespace/src/Other_module2.res ./packages/new-namespace/src/Other_module.res rewatch build &> /dev/null mv ./packages/main/src/ModuleWithInterface.resi ./packages/main/src/ModuleWithInterface2.resi -rewatch build &> ../tests/snapshots/rename-interface-file.txt +rewatch build --no-timing --snapshot-output &> ../tests/snapshots/rename-interface-file.txt # normalize paths so the snapshot is the same on all machines normalize_paths ../tests/snapshots/rename-interface-file.txt mv ./packages/main/src/ModuleWithInterface2.resi ./packages/main/src/ModuleWithInterface.resi rewatch build &> /dev/null mv ./packages/main/src/ModuleWithInterface.res ./packages/main/src/ModuleWithInterface2.res -rewatch build &> ../tests/snapshots/rename-file-with-interface.txt +rewatch build --no-timing --snapshot-output &> ../tests/snapshots/rename-file-with-interface.txt # normalize paths so the snapshot is the same on all machines normalize_paths ../tests/snapshots/rename-file-with-interface.txt mv ./packages/main/src/ModuleWithInterface2.res ./packages/main/src/ModuleWithInterface.res @@ -66,7 +66,7 @@ rewatch build &> /dev/null # when deleting a file that other files depend on, the compile should fail rm packages/dep02/src/Dep02.res -rewatch build &> ../tests/snapshots/remove-file.txt +rewatch build --no-timing --snapshot-output &> ../tests/snapshots/remove-file.txt # normalize paths so the snapshot is the same on all machines normalize_paths ../tests/snapshots/remove-file.txt git checkout -- packages/dep02/src/Dep02.res @@ -74,7 +74,7 @@ rewatch build &> /dev/null # it should show an error when we have a dependency cycle echo 'Dep01.log()' >> packages/new-namespace/src/NS_alias.res -rewatch build &> ../tests/snapshots/dependency-cycle.txt +rewatch build --no-timing --snapshot-output &> ../tests/snapshots/dependency-cycle.txt git checkout -- packages/new-namespace/src/NS_alias.res # it should compile dev dependencies with the --dev flag @@ -95,7 +95,7 @@ else exit 1 fi -rewatch clean --dev &> /dev/null +rewatch clean &> /dev/null file_count=$(find ./packages/with-dev-deps -name *.mjs | wc -l) if [ "$file_count" -eq 0 ]; then diff --git a/rewatch/tests/utils.sh b/rewatch/tests/utils.sh index 1dffbe8a8d..bef51f9fce 100644 --- a/rewatch/tests/utils.sh +++ b/rewatch/tests/utils.sh @@ -3,8 +3,8 @@ overwrite() { echo -e "\r\033[1A\033[0K$@"; } success() { echo -e "- ✅ \033[32m$1\033[0m"; } error() { echo -e "- 🛑 \033[31m$1\033[0m"; } bold() { echo -e "\033[1m$1\033[0m"; } -rewatch() { RUST_BACKTRACE=1 $REWATCH_EXECUTABLE --no-timing=true --snapshot-output=true $@; } -rewatch_bg() { RUST_BACKTRACE=1 nohup $REWATCH_EXECUTABLE --no-timing=true --snapshot-output=true $@; } +rewatch() { RUST_BACKTRACE=1 $REWATCH_EXECUTABLE $@; } +rewatch_bg() { RUST_BACKTRACE=1 nohup $REWATCH_EXECUTABLE $@; } # Detect if running on Windows is_windows() { From 110ba77a28fa0a61677d4f2de5017af917705896 Mon Sep 17 00:00:00 2001 From: Bushuo Date: Mon, 16 Jun 2025 21:47:10 +0200 Subject: [PATCH 03/22] test: update cli arg ordering --- rewatch/tests/compile.sh | 14 +++++++------- rewatch/tests/suite-ci.sh | 5 ++++- rewatch/tests/utils.sh | 4 ++-- 3 files changed, 13 insertions(+), 10 deletions(-) diff --git a/rewatch/tests/compile.sh b/rewatch/tests/compile.sh index 9fc6ebb4bc..f694b3b0bb 100755 --- a/rewatch/tests/compile.sh +++ b/rewatch/tests/compile.sh @@ -33,32 +33,32 @@ fi node ./packages/main/src/Main.mjs > ./packages/main/src/output.txt mv ./packages/main/src/Main.res ./packages/main/src/Main2.res -rewatch build --no-timing --snapshot-output &> ../tests/snapshots/rename-file.txt +rewatch build --snapshot-output &> ../tests/snapshots/rename-file.txt mv ./packages/main/src/Main2.res ./packages/main/src/Main.res # Rename a file with a dependent - this should trigger an error mv ./packages/main/src/InternalDep.res ./packages/main/src/InternalDep2.res -rewatch build --no-timing --snapshot-output &> ../tests/snapshots/rename-file-internal-dep.txt +rewatch build --snapshot-output &> ../tests/snapshots/rename-file-internal-dep.txt # normalize paths so the snapshot is the same on all machines normalize_paths ../tests/snapshots/rename-file-internal-dep.txt mv ./packages/main/src/InternalDep2.res ./packages/main/src/InternalDep.res # Rename a file with a dependent in a namespaced package - this should trigger an error (regression) mv ./packages/new-namespace/src/Other_module.res ./packages/new-namespace/src/Other_module2.res -rewatch build --no-timing --snapshot-output &> ../tests/snapshots/rename-file-internal-dep-namespace.txt +rewatch build --snapshot-output &> ../tests/snapshots/rename-file-internal-dep-namespace.txt # normalize paths so the snapshot is the same on all machines normalize_paths ../tests/snapshots/rename-file-internal-dep-namespace.txt mv ./packages/new-namespace/src/Other_module2.res ./packages/new-namespace/src/Other_module.res rewatch build &> /dev/null mv ./packages/main/src/ModuleWithInterface.resi ./packages/main/src/ModuleWithInterface2.resi -rewatch build --no-timing --snapshot-output &> ../tests/snapshots/rename-interface-file.txt +rewatch build --snapshot-output &> ../tests/snapshots/rename-interface-file.txt # normalize paths so the snapshot is the same on all machines normalize_paths ../tests/snapshots/rename-interface-file.txt mv ./packages/main/src/ModuleWithInterface2.resi ./packages/main/src/ModuleWithInterface.resi rewatch build &> /dev/null mv ./packages/main/src/ModuleWithInterface.res ./packages/main/src/ModuleWithInterface2.res -rewatch build --no-timing --snapshot-output &> ../tests/snapshots/rename-file-with-interface.txt +rewatch build --snapshot-output &> ../tests/snapshots/rename-file-with-interface.txt # normalize paths so the snapshot is the same on all machines normalize_paths ../tests/snapshots/rename-file-with-interface.txt mv ./packages/main/src/ModuleWithInterface2.res ./packages/main/src/ModuleWithInterface.res @@ -66,7 +66,7 @@ rewatch build &> /dev/null # when deleting a file that other files depend on, the compile should fail rm packages/dep02/src/Dep02.res -rewatch build --no-timing --snapshot-output &> ../tests/snapshots/remove-file.txt +rewatch build --snapshot-output &> ../tests/snapshots/remove-file.txt # normalize paths so the snapshot is the same on all machines normalize_paths ../tests/snapshots/remove-file.txt git checkout -- packages/dep02/src/Dep02.res @@ -74,7 +74,7 @@ rewatch build &> /dev/null # it should show an error when we have a dependency cycle echo 'Dep01.log()' >> packages/new-namespace/src/NS_alias.res -rewatch build --no-timing --snapshot-output &> ../tests/snapshots/dependency-cycle.txt +rewatch build --snapshot-output &> ../tests/snapshots/dependency-cycle.txt git checkout -- packages/new-namespace/src/NS_alias.res # it should compile dev dependencies with the --dev flag diff --git a/rewatch/tests/suite-ci.sh b/rewatch/tests/suite-ci.sh index d36319b988..9e5eefe1a8 100755 --- a/rewatch/tests/suite-ci.sh +++ b/rewatch/tests/suite-ci.sh @@ -8,10 +8,13 @@ cd $(dirname $0) # Get rewatch executable location from the first argument or use default if [ -n "$1" ]; then REWATCH_EXECUTABLE="$1" + BSC_PATH="" else - REWATCH_EXECUTABLE="../target/release/rewatch --bsc-path ../../_build/install/default/bin/bsc" + REWATCH_EXECUTABLE="../target/release/rewatch" + BSC_PATH="--bsc-path ../../_build/install/default/bin/bsc" fi export REWATCH_EXECUTABLE +export BSC_PATH source ./utils.sh diff --git a/rewatch/tests/utils.sh b/rewatch/tests/utils.sh index bef51f9fce..44a22ba0e3 100644 --- a/rewatch/tests/utils.sh +++ b/rewatch/tests/utils.sh @@ -3,8 +3,8 @@ overwrite() { echo -e "\r\033[1A\033[0K$@"; } success() { echo -e "- ✅ \033[32m$1\033[0m"; } error() { echo -e "- 🛑 \033[31m$1\033[0m"; } bold() { echo -e "\033[1m$1\033[0m"; } -rewatch() { RUST_BACKTRACE=1 $REWATCH_EXECUTABLE $@; } -rewatch_bg() { RUST_BACKTRACE=1 nohup $REWATCH_EXECUTABLE $@; } +rewatch() { RUST_BACKTRACE=1 $REWATCH_EXECUTABLE $@ $BSC_PATH; } +rewatch_bg() { RUST_BACKTRACE=1 nohup $REWATCH_EXECUTABLE $@ $BSC_PATH; } # Detect if running on Windows is_windows() { From 9859117877e9ac4418db33ee9cbd28ab3272e139 Mon Sep 17 00:00:00 2001 From: Bushuo Date: Wed, 18 Jun 2025 20:39:14 +0200 Subject: [PATCH 04/22] fix: look for rescript.exe not rescript-legacy --- rewatch/src/helpers.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/rewatch/src/helpers.rs b/rewatch/src/helpers.rs index b05dc9b2ad..358c4c6ef1 100644 --- a/rewatch/src/helpers.rs +++ b/rewatch/src/helpers.rs @@ -233,7 +233,7 @@ pub fn get_rescript_legacy(root_path: &Path, workspace_root: Option) -> .join("@rescript") .join(subfolder) .join("bin") - .join("rescript-legacy"); + .join("rescript.exe"); match ( root_path From 46c8454987039499c979f0af3b962482ff04ea41 Mon Sep 17 00:00:00 2001 From: Bushuo Date: Wed, 18 Jun 2025 23:55:36 +0200 Subject: [PATCH 05/22] test: add legacy test repo --- .../packages/compiled-by-legacy/package.json | 9 +++++++++ .../packages/compiled-by-legacy/rescript.json | 12 ++++++++++++ .../packages/compiled-by-legacy/src/Main.res | 1 + .../packages/compiled-by-legacy/src/Main.res.js | 9 +++++++++ 4 files changed, 31 insertions(+) create mode 100644 rewatch/testrepo/packages/compiled-by-legacy/package.json create mode 100644 rewatch/testrepo/packages/compiled-by-legacy/rescript.json create mode 100644 rewatch/testrepo/packages/compiled-by-legacy/src/Main.res create mode 100644 rewatch/testrepo/packages/compiled-by-legacy/src/Main.res.js diff --git a/rewatch/testrepo/packages/compiled-by-legacy/package.json b/rewatch/testrepo/packages/compiled-by-legacy/package.json new file mode 100644 index 0000000000..34d940f905 --- /dev/null +++ b/rewatch/testrepo/packages/compiled-by-legacy/package.json @@ -0,0 +1,9 @@ +{ + "name": "@testrepo/compiled-by-legacy", + "version": "0.0.1", + "keywords": [ + "rescript" + ], + "author": "", + "license": "MIT" +} diff --git a/rewatch/testrepo/packages/compiled-by-legacy/rescript.json b/rewatch/testrepo/packages/compiled-by-legacy/rescript.json new file mode 100644 index 0000000000..f94702ab3e --- /dev/null +++ b/rewatch/testrepo/packages/compiled-by-legacy/rescript.json @@ -0,0 +1,12 @@ +{ + "name": "@testrepo/compiled-by-legacy", + "sources": { + "dir": "src", + "subdirs": true + }, + "package-specs": { + "module": "es6", + "in-source": true + }, + "suffix": ".res.js" +} diff --git a/rewatch/testrepo/packages/compiled-by-legacy/src/Main.res b/rewatch/testrepo/packages/compiled-by-legacy/src/Main.res new file mode 100644 index 0000000000..3b0c82647f --- /dev/null +++ b/rewatch/testrepo/packages/compiled-by-legacy/src/Main.res @@ -0,0 +1 @@ +let x = 1 \ No newline at end of file diff --git a/rewatch/testrepo/packages/compiled-by-legacy/src/Main.res.js b/rewatch/testrepo/packages/compiled-by-legacy/src/Main.res.js new file mode 100644 index 0000000000..618d7a44e8 --- /dev/null +++ b/rewatch/testrepo/packages/compiled-by-legacy/src/Main.res.js @@ -0,0 +1,9 @@ +// Generated by ReScript, PLEASE EDIT WITH CARE + + +let x = 1; + +export { + x, +} +/* No side effect */ From b4a1dbb4a8357f593a83588a12cbd854cad75fbc Mon Sep 17 00:00:00 2001 From: Bushuo Date: Thu, 19 Jun 2025 00:10:37 +0200 Subject: [PATCH 06/22] test: add legacy build system compile tests --- rewatch/tests/legacy-utils.sh | 3 +++ rewatch/tests/legacy.sh | 28 ++++++++++++++++++++++++++++ rewatch/tests/suffix.sh | 2 +- rewatch/tests/suite-ci.sh | 2 +- 4 files changed, 33 insertions(+), 2 deletions(-) create mode 100644 rewatch/tests/legacy-utils.sh create mode 100755 rewatch/tests/legacy.sh diff --git a/rewatch/tests/legacy-utils.sh b/rewatch/tests/legacy-utils.sh new file mode 100644 index 0000000000..3899df52c8 --- /dev/null +++ b/rewatch/tests/legacy-utils.sh @@ -0,0 +1,3 @@ +source "utils.sh" + +rewatch_legacy() { RUST_BACKTRACE=1 "../../$REWATCH_EXECUTABLE" legacy $@; } \ No newline at end of file diff --git a/rewatch/tests/legacy.sh b/rewatch/tests/legacy.sh new file mode 100755 index 0000000000..231029534c --- /dev/null +++ b/rewatch/tests/legacy.sh @@ -0,0 +1,28 @@ +source "./legacy-utils.sh" +cd ../testrepo/packages/compiled-by-legacy + +bold "Test: It should use the legacy build system" + +if rewatch_legacy clean &> /dev/null; +then + success "Test package cleaned" +else + error "Error cleaning test package" + exit 1 +fi + +if rewatch_legacy build &> /dev/null; +then + success "Test package built" +else + error "Error building test package" + exit 1 +fi + +if git diff --exit-code ./; +then + success "Test package has no changes" +else + error "Build has changed" + exit 1 +fi diff --git a/rewatch/tests/suffix.sh b/rewatch/tests/suffix.sh index 3768005297..f51ca93306 100755 --- a/rewatch/tests/suffix.sh +++ b/rewatch/tests/suffix.sh @@ -27,7 +27,7 @@ fi # Count files with new extension file_count=$(find ./packages -name *.res.js | wc -l) -if [ "$file_count" -eq 24 ]; +if [ "$file_count" -eq 25 ]; then success "Found files with correct suffix" else diff --git a/rewatch/tests/suite-ci.sh b/rewatch/tests/suite-ci.sh index 9e5eefe1a8..fd5f11544b 100755 --- a/rewatch/tests/suite-ci.sh +++ b/rewatch/tests/suite-ci.sh @@ -40,4 +40,4 @@ else exit 1 fi -./compile.sh && ./watch.sh && ./lock.sh && ./suffix.sh +./compile.sh && ./watch.sh && ./lock.sh && ./suffix.sh && ./legacy.sh From aaed46593732a85b158c6f3b425b37a05c98608c Mon Sep 17 00:00:00 2001 From: Bushuo Date: Thu, 19 Jun 2025 22:48:01 +0200 Subject: [PATCH 07/22] test: print stderr output on failure --- rewatch/tests/legacy.sh | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/rewatch/tests/legacy.sh b/rewatch/tests/legacy.sh index 231029534c..b3d5c3e029 100755 --- a/rewatch/tests/legacy.sh +++ b/rewatch/tests/legacy.sh @@ -3,19 +3,25 @@ cd ../testrepo/packages/compiled-by-legacy bold "Test: It should use the legacy build system" -if rewatch_legacy clean &> /dev/null; +error_output=$(rewatch_legacy clean 2>&1 >/dev/null) + +if [ $? -eq 0 ]; then success "Test package cleaned" else error "Error cleaning test package" + printf "%s\n" "$error_output" >&2 exit 1 fi -if rewatch_legacy build &> /dev/null; +error_output=$(rewatch_legacy build 2>&1 >/dev/null) + +if [ $? -eq 0 ]; then success "Test package built" else error "Error building test package" + printf "%s\n" "$error_output" >&2 exit 1 fi From 107e5106ee3824459dbe67c0dff293b0c7c06ae1 Mon Sep 17 00:00:00 2001 From: Bushuo Date: Fri, 20 Jun 2025 01:05:36 +0200 Subject: [PATCH 08/22] refactor: extract fn to get binary dir --- rewatch/src/helpers.rs | 45 +++++++++++++++++------------------------- 1 file changed, 18 insertions(+), 27 deletions(-) diff --git a/rewatch/src/helpers.rs b/rewatch/src/helpers.rs index 358c4c6ef1..61f68272ed 100644 --- a/rewatch/src/helpers.rs +++ b/rewatch/src/helpers.rs @@ -181,7 +181,7 @@ pub fn create_path_for_path(path: &Path) { fs::DirBuilder::new().recursive(true).create(path).unwrap(); } -pub fn get_bsc(root_path: &Path, workspace_root: &Option) -> PathBuf { +fn get_bin_dir() -> PathBuf { let subfolder = match (std::env::consts::OS, std::env::consts::ARCH) { ("macos", "aarch64") => "darwin-arm64", ("macos", _) => "darwin-x64", @@ -192,21 +192,24 @@ pub fn get_bsc(root_path: &Path, workspace_root: &Option) -> PathBuf { _ => panic!("Unsupported architecture"), }; + Path::new("node_modules") + .join("@rescript") + .join(subfolder) + .join("bin") +} + +pub fn get_bsc(root_path: &Path, workspace_root: &Option) -> PathBuf { + let bin_dir = get_bin_dir(); + match ( root_path - .join("node_modules") - .join("@rescript") - .join(subfolder) - .join("bin") + .join(&bin_dir) .join("bsc.exe") .canonicalize() .map(StrippedVerbatimPath::to_stripped_verbatim_path), workspace_root.as_ref().map(|workspace_root| { workspace_root - .join("node_modules") - .join("@rescript") - .join(subfolder) - .join("bin") + .join(&bin_dir) .join("bsc.exe") .canonicalize() .map(StrippedVerbatimPath::to_stripped_verbatim_path) @@ -219,37 +222,25 @@ pub fn get_bsc(root_path: &Path, workspace_root: &Option) -> PathBuf { } pub fn get_rescript_legacy(root_path: &Path, workspace_root: Option) -> PathBuf { - let subfolder = match (std::env::consts::OS, std::env::consts::ARCH) { - ("macos", "aarch64") => "darwin-arm64", - ("macos", _) => "darwin-x64", - ("linux", "aarch64") => "linux-arm64", - ("linux", _) => "linux-x64", - ("windows", "aarch64") => "win-arm64", - ("windows", _) => "win-x64", - _ => panic!("Unsupported architecture"), - }; - - let legacy_path_fragment = Path::new("node_modules") - .join("@rescript") - .join(subfolder) - .join("bin") - .join("rescript.exe"); + let bin_dir = get_bin_dir(); match ( root_path - .join(&legacy_path_fragment) + .join(&bin_dir) + .join("rescript.exe") .canonicalize() .map(StrippedVerbatimPath::to_stripped_verbatim_path), workspace_root.map(|workspace_root| { workspace_root - .join(&legacy_path_fragment) + .join(&bin_dir) + .join("rescript.exe") .canonicalize() .map(StrippedVerbatimPath::to_stripped_verbatim_path) }), ) { (Ok(path), _) => path, (_, Some(Ok(path))) => path, - _ => panic!("Could not find rescript-legacy"), + _ => panic!("Could not find rescript.exe"), } } From 18dddc3c177a76707fb9d411a0bb6bf47ca6d66c Mon Sep 17 00:00:00 2001 From: Bushuo Date: Fri, 20 Jun 2025 23:13:11 +0200 Subject: [PATCH 09/22] fix: windows binary path --- rewatch/src/helpers.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/rewatch/src/helpers.rs b/rewatch/src/helpers.rs index 61f68272ed..5b9c93dc61 100644 --- a/rewatch/src/helpers.rs +++ b/rewatch/src/helpers.rs @@ -188,7 +188,7 @@ fn get_bin_dir() -> PathBuf { ("linux", "aarch64") => "linux-arm64", ("linux", _) => "linux-x64", ("windows", "aarch64") => "win-arm64", - ("windows", _) => "win-x64", + ("windows", _) => "win32-x64", _ => panic!("Unsupported architecture"), }; From 66974f9b7ee4254ab95652d3eb639ba40313bb5b Mon Sep 17 00:00:00 2001 From: Bushuo Date: Sat, 21 Jun 2025 19:22:23 +0200 Subject: [PATCH 10/22] fix: pass bsc-path arg only to specific subcommands --- cli/rewatch.js | 36 +++++++++++++++++++++++++++++++++--- 1 file changed, 33 insertions(+), 3 deletions(-) diff --git a/cli/rewatch.js b/cli/rewatch.js index 6df646ed4b..fed7289d45 100755 --- a/cli/rewatch.js +++ b/cli/rewatch.js @@ -7,6 +7,36 @@ import { rewatch_exe, bsc_exe } from "./common/bins.js"; const args = process.argv.slice(2); -child_process.spawnSync(rewatch_exe, [...args, "--bsc-path", bsc_exe], { - stdio: "inherit", -}); +const firstPositionalArgIndex = args.findIndex((arg) => !arg.startsWith("-")); + +try { + if (firstPositionalArgIndex !== -1) { + const subcommand = args[firstPositionalArgIndex]; + const subcommandArgs = args.slice(firstPositionalArgIndex + 1); + + if ( + subcommand === "build" || + subcommand === "watch" || + subcommand === "clean" || + subcommand === "compiler-args" + ) { + child_process.execFileSync( + rewatch_exe, + [...subcommandArgs, "--bsc-path", bsc_exe], + { + stdio: "inherit", + } + ); + } else { + child_process.execFileSync(rewatch_exe, [...args], { + stdio: "inherit", + }); + } + } +} catch (err) { + if (err.status !== undefined) { + process.exit(err.status); // Pass through the exit code + } else { + process.exit(1); // Generic error + } +} From d2c561de8835aee97a39a9fa05b98a41357245e5 Mon Sep 17 00:00:00 2001 From: Bushuo Date: Sun, 22 Jun 2025 19:27:34 +0200 Subject: [PATCH 11/22] test: add package to testrepo deps --- rewatch/testrepo/bsconfig.json | 6 ++++-- rewatch/testrepo/package.json | 3 ++- .../testrepo/packages/compiled-by-legacy/rescript.json | 1 + .../testrepo/packages/compiled-by-legacy/src/Main.mjs | 9 +++++++++ rewatch/testrepo/packages/main/package.json | 1 + rewatch/testrepo/yarn.lock | 7 +++++++ 6 files changed, 24 insertions(+), 3 deletions(-) create mode 100644 rewatch/testrepo/packages/compiled-by-legacy/src/Main.mjs diff --git a/rewatch/testrepo/bsconfig.json b/rewatch/testrepo/bsconfig.json index 706ee9066a..95e49a9f45 100644 --- a/rewatch/testrepo/bsconfig.json +++ b/rewatch/testrepo/bsconfig.json @@ -20,7 +20,8 @@ "@testrepo/dep02", "@testrepo/new-namespace", "@testrepo/namespace-casing", - "@testrepo/with-dev-deps" + "@testrepo/with-dev-deps", + "@testrepo/compiled-by-legacy" ], "bs-dependencies": [ "@testrepo/main", @@ -28,7 +29,8 @@ "@testrepo/dep02", "@testrepo/new-namespace", "@testrepo/namespace-casing", - "@testrepo/with-dev-deps" + "@testrepo/with-dev-deps", + "@testrepo/compiled-by-legacy" ], "reason": { "react-jsx": 3 diff --git a/rewatch/testrepo/package.json b/rewatch/testrepo/package.json index 3436184038..2ed3978be5 100644 --- a/rewatch/testrepo/package.json +++ b/rewatch/testrepo/package.json @@ -8,7 +8,8 @@ "packages/dep02", "packages/new-namespace", "packages/namespace-casing", - "packages/with-dev-deps" + "packages/with-dev-deps", + "packages/compiled-by-legacy" ] }, "dependencies": { diff --git a/rewatch/testrepo/packages/compiled-by-legacy/rescript.json b/rewatch/testrepo/packages/compiled-by-legacy/rescript.json index f94702ab3e..d62afdf93c 100644 --- a/rewatch/testrepo/packages/compiled-by-legacy/rescript.json +++ b/rewatch/testrepo/packages/compiled-by-legacy/rescript.json @@ -1,5 +1,6 @@ { "name": "@testrepo/compiled-by-legacy", + "namespace": true, "sources": { "dir": "src", "subdirs": true diff --git a/rewatch/testrepo/packages/compiled-by-legacy/src/Main.mjs b/rewatch/testrepo/packages/compiled-by-legacy/src/Main.mjs new file mode 100644 index 0000000000..618d7a44e8 --- /dev/null +++ b/rewatch/testrepo/packages/compiled-by-legacy/src/Main.mjs @@ -0,0 +1,9 @@ +// Generated by ReScript, PLEASE EDIT WITH CARE + + +let x = 1; + +export { + x, +} +/* No side effect */ diff --git a/rewatch/testrepo/packages/main/package.json b/rewatch/testrepo/packages/main/package.json index 10954e0797..1813de299d 100644 --- a/rewatch/testrepo/packages/main/package.json +++ b/rewatch/testrepo/packages/main/package.json @@ -12,6 +12,7 @@ "author": "", "license": "MIT", "dependencies": { + "@testrepo/compiled-by-legacy": "*", "@testrepo/dep01": "*" } } diff --git a/rewatch/testrepo/yarn.lock b/rewatch/testrepo/yarn.lock index ac41b3d2c1..beb6bf912d 100644 --- a/rewatch/testrepo/yarn.lock +++ b/rewatch/testrepo/yarn.lock @@ -40,6 +40,12 @@ __metadata: languageName: node linkType: hard +"@testrepo/compiled-by-legacy@npm:*, @testrepo/compiled-by-legacy@workspace:packages/compiled-by-legacy": + version: 0.0.0-use.local + resolution: "@testrepo/compiled-by-legacy@workspace:packages/compiled-by-legacy" + languageName: unknown + linkType: soft + "@testrepo/dep01@npm:*, @testrepo/dep01@workspace:packages/dep01": version: 0.0.0-use.local resolution: "@testrepo/dep01@workspace:packages/dep01" @@ -58,6 +64,7 @@ __metadata: version: 0.0.0-use.local resolution: "@testrepo/main@workspace:packages/main" dependencies: + "@testrepo/compiled-by-legacy": "npm:*" "@testrepo/dep01": "npm:*" languageName: unknown linkType: soft From 7742361212e86e724887bf9f58f3154ee9f2ef83 Mon Sep 17 00:00:00 2001 From: Bushuo Date: Sun, 22 Jun 2025 19:46:58 +0200 Subject: [PATCH 12/22] test: update snapshots --- rewatch/tests/snapshots/dependency-cycle.txt | 2 +- rewatch/tests/snapshots/remove-file.txt | 2 +- rewatch/tests/snapshots/rename-file-internal-dep-namespace.txt | 2 +- rewatch/tests/snapshots/rename-file-internal-dep.txt | 2 +- rewatch/tests/snapshots/rename-file-with-interface.txt | 2 +- rewatch/tests/snapshots/rename-file.txt | 2 +- rewatch/tests/snapshots/rename-interface-file.txt | 2 +- rewatch/tests/suffix.sh | 2 +- 8 files changed, 8 insertions(+), 8 deletions(-) diff --git a/rewatch/tests/snapshots/dependency-cycle.txt b/rewatch/tests/snapshots/dependency-cycle.txt index c949d4005c..c6d7f793e8 100644 --- a/rewatch/tests/snapshots/dependency-cycle.txt +++ b/rewatch/tests/snapshots/dependency-cycle.txt @@ -1,4 +1,4 @@ -Cleaned 0/14 +Cleaned 0/15 Parsed 1 source files Compiled 0 modules diff --git a/rewatch/tests/snapshots/remove-file.txt b/rewatch/tests/snapshots/remove-file.txt index 921f9d4246..8d68cdd418 100644 --- a/rewatch/tests/snapshots/remove-file.txt +++ b/rewatch/tests/snapshots/remove-file.txt @@ -1,4 +1,4 @@ -Cleaned 1/14 +Cleaned 1/15 Parsed 0 source files Compiled 1 modules diff --git a/rewatch/tests/snapshots/rename-file-internal-dep-namespace.txt b/rewatch/tests/snapshots/rename-file-internal-dep-namespace.txt index 1950bad9e3..3263c0fe88 100644 --- a/rewatch/tests/snapshots/rename-file-internal-dep-namespace.txt +++ b/rewatch/tests/snapshots/rename-file-internal-dep-namespace.txt @@ -1,4 +1,4 @@ -Cleaned 2/14 +Cleaned 2/15 Parsed 2 source files Compiled 3 modules diff --git a/rewatch/tests/snapshots/rename-file-internal-dep.txt b/rewatch/tests/snapshots/rename-file-internal-dep.txt index f81a6dece4..829a187871 100644 --- a/rewatch/tests/snapshots/rename-file-internal-dep.txt +++ b/rewatch/tests/snapshots/rename-file-internal-dep.txt @@ -1,4 +1,4 @@ -Cleaned 2/14 +Cleaned 2/15 Parsed 2 source files Compiled 2 modules diff --git a/rewatch/tests/snapshots/rename-file-with-interface.txt b/rewatch/tests/snapshots/rename-file-with-interface.txt index 257fba3570..e784d71b9e 100644 --- a/rewatch/tests/snapshots/rename-file-with-interface.txt +++ b/rewatch/tests/snapshots/rename-file-with-interface.txt @@ -1,4 +1,4 @@  No implementation file found for interface file (skipping): src/ModuleWithInterface.resi -Cleaned 2/14 +Cleaned 2/15 Parsed 1 source files Compiled 2 modules diff --git a/rewatch/tests/snapshots/rename-file.txt b/rewatch/tests/snapshots/rename-file.txt index 5b20d86fd7..5458530d74 100644 --- a/rewatch/tests/snapshots/rename-file.txt +++ b/rewatch/tests/snapshots/rename-file.txt @@ -1,3 +1,3 @@ -Cleaned 1/14 +Cleaned 1/15 Parsed 1 source files Compiled 1 modules diff --git a/rewatch/tests/snapshots/rename-interface-file.txt b/rewatch/tests/snapshots/rename-interface-file.txt index e2d7fd9752..26d7ffe3e6 100644 --- a/rewatch/tests/snapshots/rename-interface-file.txt +++ b/rewatch/tests/snapshots/rename-interface-file.txt @@ -1,4 +1,4 @@  No implementation file found for interface file (skipping): src/ModuleWithInterface2.resi -Cleaned 1/14 +Cleaned 1/15 Parsed 1 source files Compiled 2 modules diff --git a/rewatch/tests/suffix.sh b/rewatch/tests/suffix.sh index f51ca93306..d644a34e99 100755 --- a/rewatch/tests/suffix.sh +++ b/rewatch/tests/suffix.sh @@ -27,7 +27,7 @@ fi # Count files with new extension file_count=$(find ./packages -name *.res.js | wc -l) -if [ "$file_count" -eq 25 ]; +if [ "$file_count" -eq 26 ]; then success "Found files with correct suffix" else From fb9400cedcb5aa48d2203a9e671b4fb4fdd68c55 Mon Sep 17 00:00:00 2001 From: Bushuo Date: Sun, 22 Jun 2025 20:03:07 +0200 Subject: [PATCH 13/22] test: improve test output --- rewatch/tests/compile.sh | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/rewatch/tests/compile.sh b/rewatch/tests/compile.sh index f694b3b0bb..a465933c9e 100755 --- a/rewatch/tests/compile.sh +++ b/rewatch/tests/compile.sh @@ -87,21 +87,23 @@ then fi file_count=$(find ./packages/with-dev-deps/test -name *.mjs | wc -l) -if [ "$file_count" -eq 1 ]; +expected_file_count=1 +if [ "$file_count" -eq $expected_file_count ]; then success "Compiled dev dependencies successfully" else - error "Expected 2 files to be compiled with the --dev flag, found $file_count" + error "Expected $expected_file_count files to be compiled with the --dev flag, found $file_count" exit 1 fi -rewatch clean &> /dev/null +error_output=$(rewatch clean 2>&1 >/dev/null) file_count=$(find ./packages/with-dev-deps -name *.mjs | wc -l) if [ "$file_count" -eq 0 ]; then success "Cleaned dev dependencies successfully" else error "Expected 0 files remaining after cleaning, found $file_count" + printf "%s\n" "$error_output" >&2 exit 1 fi From 9bf9d43048543ea6fd86e43b590ce364b3e4f9a8 Mon Sep 17 00:00:00 2001 From: Bushuo Date: Mon, 23 Jun 2025 09:24:25 +0200 Subject: [PATCH 14/22] fix: args passing in cli wrapper --- cli/rewatch.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/cli/rewatch.js b/cli/rewatch.js index fed7289d45..d363ebe477 100755 --- a/cli/rewatch.js +++ b/cli/rewatch.js @@ -12,7 +12,7 @@ const firstPositionalArgIndex = args.findIndex((arg) => !arg.startsWith("-")); try { if (firstPositionalArgIndex !== -1) { const subcommand = args[firstPositionalArgIndex]; - const subcommandArgs = args.slice(firstPositionalArgIndex + 1); + const subcommandWithArgs = args.slice(firstPositionalArgIndex); if ( subcommand === "build" || @@ -22,7 +22,7 @@ try { ) { child_process.execFileSync( rewatch_exe, - [...subcommandArgs, "--bsc-path", bsc_exe], + [...subcommandWithArgs, "--bsc-path", bsc_exe], { stdio: "inherit", } From 7faf311279d3eafc91666b1662cb4409df9be008 Mon Sep 17 00:00:00 2001 From: Bushuo Date: Mon, 23 Jun 2025 21:09:35 +0200 Subject: [PATCH 15/22] fix: pass `--bsc-path` to implicit build command --- cli/rewatch.js | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/cli/rewatch.js b/cli/rewatch.js index d363ebe477..d7e65e077e 100755 --- a/cli/rewatch.js +++ b/cli/rewatch.js @@ -32,6 +32,11 @@ try { stdio: "inherit", }); } + } else { + // no subcommand means build subcommand + child_process.execFileSync(rewatch_exe, [...args, "--bsc-path", bsc_exe], { + stdio: "inherit", + }); } } catch (err) { if (err.status !== undefined) { From b730d9f1419645507a0cd7c9f4d1c8409d07d4ef Mon Sep 17 00:00:00 2001 From: Bushuo Date: Sat, 28 Jun 2025 23:21:12 +0200 Subject: [PATCH 16/22] fix: wrong path to `rescript` executable refactor `cli.rs` to remove duplication of docstrings --- rewatch/src/build.rs | 10 +- rewatch/src/build/clean.rs | 2 +- rewatch/src/cli.rs | 193 ++++++++++++------ rewatch/src/helpers.rs | 6 +- rewatch/src/main.rs | 172 ++++++++-------- .../packages/compiled-by-legacy/rescript.json | 2 +- rewatch/tests/legacy.sh | 26 ++- 7 files changed, 256 insertions(+), 155 deletions(-) diff --git a/rewatch/src/build.rs b/rewatch/src/build.rs index ab00db8aad..50ab16a216 100644 --- a/rewatch/src/build.rs +++ b/rewatch/src/build.rs @@ -59,7 +59,7 @@ pub struct CompilerArgs { pub fn get_compiler_args( path: &Path, rescript_version: Option, - bsc_path: &Option, + bsc_path: Option, build_dev_deps: bool, ) -> Result { let filename = &helpers::get_abs_path(path); @@ -501,7 +501,7 @@ pub fn build( show_progress: bool, no_timing: bool, create_sourcedirs: bool, - bsc_path: &Option, + bsc_path: Option, build_dev_deps: bool, snapshot_output: bool, ) -> Result { @@ -516,7 +516,7 @@ pub fn build( filter, show_progress, path, - bsc_path, + &bsc_path, build_dev_deps, snapshot_output, ) @@ -558,9 +558,9 @@ pub fn pass_through_legacy(args: Vec) -> i32 { let project_root = helpers::get_abs_path(Path::new(".")); let workspace_root = helpers::get_workspace_root(&project_root); - let bsb_path = helpers::get_rescript_legacy(&project_root, workspace_root); + let rescript_legacy_path = helpers::get_rescript_legacy(&project_root, workspace_root); - let status = std::process::Command::new(bsb_path) + let status = std::process::Command::new(rescript_legacy_path) .args(args) .stdout(Stdio::inherit()) .stderr(Stdio::inherit()) diff --git a/rewatch/src/build/clean.rs b/rewatch/src/build/clean.rs index 0057437997..8a09bef035 100644 --- a/rewatch/src/build/clean.rs +++ b/rewatch/src/build/clean.rs @@ -334,7 +334,7 @@ pub fn cleanup_after_build(build_state: &BuildState) { pub fn clean( path: &Path, show_progress: bool, - bsc_path: &Option, + bsc_path: Option, snapshot_output: bool, ) -> Result<()> { let project_root = helpers::get_abs_path(path); diff --git a/rewatch/src/cli.rs b/rewatch/src/cli.rs index 87ec1efb09..d9a088d8ae 100644 --- a/rewatch/src/cli.rs +++ b/rewatch/src/cli.rs @@ -1,4 +1,4 @@ -use std::ffi::OsString; +use std::{ffi::OsString, ops::Deref}; use clap::{Args, Parser, Subcommand}; use clap_verbosity_flag::InfoLevel; @@ -24,23 +24,29 @@ pub struct Cli { #[command(subcommand)] pub command: Option, + #[command(flatten)] + pub build_args: BuildArgs, +} + +#[derive(Args, Debug, Clone)] +pub struct FolderArg { /// The relative path to where the main rescript.json resides. IE - the root of your project. #[arg(default_value = ".")] pub folder: String, - - #[command(flatten)] - pub build_args: BuildArgs, } #[derive(Args, Debug, Clone)] -pub struct BuildArgs { +pub struct FilterArg { /// Filter files by regex /// /// Filter allows for a regex to be supplied which will filter the files to be compiled. For /// instance, to filter out test files for compilation while doing feature work. #[arg(short, long)] pub filter: Option, +} +#[derive(Args, Debug, Clone)] +pub struct AfterBuildArg { /// Action after build /// /// This allows one to pass an additional command to the watcher, which allows it to run when @@ -49,14 +55,20 @@ pub struct BuildArgs { /// color as well #[arg(short, long)] pub after_build: Option, +} +#[derive(Args, Debug, Clone, Copy)] +pub struct CreateSourceDirsArg { /// Create source_dirs.json /// /// This creates a source_dirs.json file at the root of the monorepo, which is needed when you /// want to use Reanalyze #[arg(short, long, default_value_t = false, num_args = 0..=1)] pub create_sourcedirs: bool, +} +#[derive(Args, Debug, Clone, Copy)] +pub struct DevArg { /// Build development dependencies /// /// This is the flag to also compile development dependencies @@ -65,61 +77,72 @@ pub struct BuildArgs { /// _all_ packages #[arg(long, default_value_t = false, num_args = 0..=1)] pub dev: bool, +} - /// Disable timing on the output - #[arg(short, long, default_value_t = false, num_args = 0..=1)] - pub no_timing: bool, +#[derive(Args, Debug, Clone)] +pub struct BscPathArg { + /// Custom path to bsc + #[arg(long)] + pub bsc_path: Option, +} +#[derive(Args, Debug, Clone, Copy)] +pub struct SnapshotOutputArg { /// simple output for snapshot testing #[arg(short, long, default_value = "false", num_args = 0..=1)] pub snapshot_output: bool, +} - /// Path to bsc - #[arg(long)] - pub bsc_path: Option, +#[derive(Args, Debug, Clone)] +pub struct BuildArgs { + #[command(flatten)] + pub folder: FolderArg, + + #[command(flatten)] + pub filter: FilterArg, + + #[command(flatten)] + pub after_build: AfterBuildArg, + + #[command(flatten)] + pub create_sourcedirs: CreateSourceDirsArg, + + #[command(flatten)] + pub dev: DevArg, + + /// Disable timing on the output + #[arg(short, long, default_value_t = false, num_args = 0..=1)] + pub no_timing: bool, + + #[command(flatten)] + pub snapshot_output: SnapshotOutputArg, + + #[command(flatten)] + pub bsc_path: BscPathArg, } #[derive(Args, Clone, Debug)] pub struct WatchArgs { - /// Filter files by regex - /// - /// Filter allows for a regex to be supplied which will filter the files to be compiled. For - /// instance, to filter out test files for compilation while doing feature work. - #[arg(short, long)] - pub filter: Option, + #[command(flatten)] + pub folder: FolderArg, - /// Action after build - /// - /// This allows one to pass an additional command to the watcher, which allows it to run when - /// finished. For instance, to play a sound when done compiling, or to run a test suite. - /// NOTE - You may need to add '--color=always' to your subcommand in case you want to output - /// color as well - #[arg(short, long)] - pub after_build: Option, + #[command(flatten)] + pub filter: FilterArg, - /// Create source_dirs.json - /// - /// This creates a source_dirs.json file at the root of the monorepo, which is needed when you - /// want to use Reanalyze - #[arg(short, long, default_value_t = false, num_args = 0..=1)] - pub create_sourcedirs: bool, + #[command(flatten)] + pub after_build: AfterBuildArg, - /// Build development dependencies - /// - /// This is the flag to also compile development dependencies - /// It's important to know that we currently do not discern between project src, and - /// dependencies. So enabling this flag will enable building _all_ development dependencies of - /// _all_ packages - #[arg(long, default_value_t = false, num_args = 0..=1)] - pub dev: bool, + #[command(flatten)] + pub create_sourcedirs: CreateSourceDirsArg, - /// simple output for snapshot testing - #[arg(short, long, default_value = "false", num_args = 0..=1)] - pub snapshot_output: bool, + #[command(flatten)] + pub dev: DevArg, - /// Path to bsc - #[arg(long)] - pub bsc_path: Option, + #[command(flatten)] + pub snapshot_output: SnapshotOutputArg, + + #[command(flatten)] + pub bsc_path: BscPathArg, } #[derive(Subcommand, Clone, Debug)] @@ -130,13 +153,14 @@ pub enum Command { Watch(WatchArgs), /// Clean the build artifacts Clean { - /// Path to bsc - #[arg(long)] - bsc_path: Option, + #[command(flatten)] + folder: FolderArg, + + #[command(flatten)] + bsc_path: BscPathArg, - /// simple output for snapshot testing - #[arg(short, long, default_value = "false", num_args = 0..=1)] - snapshot_output: bool, + #[command(flatten)] + snapshot_output: SnapshotOutputArg, }, /// Alias to `legacy format`. #[command(disable_help_flag = true)] @@ -156,23 +180,78 @@ pub enum Command { #[command()] path: String, - #[arg(long, default_value_t = false, num_args = 0..=1)] - dev: bool, + #[command(flatten)] + dev: DevArg, /// To be used in conjunction with compiler_args #[arg(long)] rescript_version: Option, - /// A custom path to bsc - #[arg(long)] - bsc_path: Option, + #[command(flatten)] + bsc_path: BscPathArg, }, /// Use the legacy build system. /// /// After this command is encountered, the rest of the arguments are passed to the legacy build system. - #[command(disable_help_flag = true)] + #[command(disable_help_flag = true, external_subcommand = true)] Legacy { #[arg(allow_hyphen_values = true, num_args = 0..)] legacy_args: Vec, }, } + +impl Deref for FolderArg { + type Target = str; + + fn deref(&self) -> &Self::Target { + &self.folder + } +} + +impl Deref for FilterArg { + type Target = Option; + + fn deref(&self) -> &Self::Target { + &self.filter + } +} + +impl Deref for AfterBuildArg { + type Target = Option; + + fn deref(&self) -> &Self::Target { + &self.after_build + } +} + +impl Deref for CreateSourceDirsArg { + type Target = bool; + + fn deref(&self) -> &Self::Target { + &self.create_sourcedirs + } +} + +impl Deref for DevArg { + type Target = bool; + + fn deref(&self) -> &Self::Target { + &self.dev + } +} + +impl Deref for BscPathArg { + type Target = Option; + + fn deref(&self) -> &Self::Target { + &self.bsc_path + } +} + +impl Deref for SnapshotOutputArg { + type Target = bool; + + fn deref(&self) -> &Self::Target { + &self.snapshot_output + } +} diff --git a/rewatch/src/helpers.rs b/rewatch/src/helpers.rs index 5b9c93dc61..9b6661c2e4 100644 --- a/rewatch/src/helpers.rs +++ b/rewatch/src/helpers.rs @@ -222,18 +222,18 @@ pub fn get_bsc(root_path: &Path, workspace_root: &Option) -> PathBuf { } pub fn get_rescript_legacy(root_path: &Path, workspace_root: Option) -> PathBuf { - let bin_dir = get_bin_dir(); + let bin_dir = Path::new("node_modules").join("rescript").join("cli"); match ( root_path .join(&bin_dir) - .join("rescript.exe") + .join("rescript.js") .canonicalize() .map(StrippedVerbatimPath::to_stripped_verbatim_path), workspace_root.map(|workspace_root| { workspace_root .join(&bin_dir) - .join("rescript.exe") + .join("rescript.js") .canonicalize() .map(StrippedVerbatimPath::to_stripped_verbatim_path) }), diff --git a/rewatch/src/main.rs b/rewatch/src/main.rs index dcebec5945..3cd1c5d084 100644 --- a/rewatch/src/main.rs +++ b/rewatch/src/main.rs @@ -22,22 +22,11 @@ fn main() -> Result<()> { let command = args.command.unwrap_or(cli::Command::Build(args.build_args)); - // handle those commands early, because we don't need a lock for them + // The 'normal run' mode will show the 'pretty' formatted progress. But if we turn off the log + // level, we should never show that. + let show_progress = log_level_filter == LevelFilter::Info; + match command.clone() { - cli::Command::Legacy { legacy_args } => { - let code = build::pass_through_legacy(legacy_args); - std::process::exit(code); - } - cli::Command::Format { mut format_args } => { - format_args.insert(0, "format".into()); - let code = build::pass_through_legacy(format_args); - std::process::exit(code); - } - cli::Command::Dump { mut dump_args } => { - dump_args.insert(0, "dump".into()); - let code = build::pass_through_legacy(dump_args); - std::process::exit(code); - } cli::Command::CompilerArgs { path, dev, @@ -49,84 +38,99 @@ fn main() -> Result<()> { build::get_compiler_args( Path::new(&path), rescript_version, - &bsc_path.map(PathBuf::from), - dev + bsc_path.as_ref().map(PathBuf::from), + *dev )? ); std::process::exit(0); } - _ => (), - } + cli::Command::Build(build_args) => { + let _lock = get_lock(&build_args.folder); - // The 'normal run' mode will show the 'pretty' formatted progress. But if we turn off the log - // level, we should never show that. - let show_progress = log_level_filter == LevelFilter::Info; + let filter = build_args + .filter + .as_ref() + .map(|filter| Regex::new(&filter).expect("Could not parse regex")); - match lock::get(&args.folder) { - lock::Lock::Error(ref e) => { - println!("Could not start Rewatch: {e}"); - std::process::exit(1) + match build::build( + &filter, + Path::new(&build_args.folder as &str), + show_progress, + build_args.no_timing, + *build_args.create_sourcedirs, + build_args.bsc_path.as_ref().map(PathBuf::from), + *build_args.dev, + *build_args.snapshot_output, + ) { + Err(e) => { + println!("{e}"); + std::process::exit(1) + } + Ok(_) => { + if let Some(args_after_build) = (*build_args.after_build).clone() { + cmd::run(args_after_build) + } + std::process::exit(0) + } + }; } - lock::Lock::Aquired(_) => match command { - cli::Command::Clean { - bsc_path, - snapshot_output, - } => build::clean::clean( - Path::new(&args.folder), + cli::Command::Watch(watch_args) => { + let _lock = get_lock(&watch_args.folder); + + let filter = watch_args + .filter + .as_ref() + .map(|filter| Regex::new(&filter).expect("Could not parse regex")); + watcher::start( + &filter, show_progress, - &bsc_path.map(PathBuf::from), - snapshot_output, - ), - cli::Command::Build(build_args) => { - let filter = build_args - .filter - .map(|filter| Regex::new(filter.as_ref()).expect("Could not parse regex")); + &watch_args.folder, + (*watch_args.after_build).clone(), + *watch_args.create_sourcedirs, + *watch_args.dev, + (*watch_args.bsc_path).clone(), + *watch_args.snapshot_output, + ); - match build::build( - &filter, - Path::new(&args.folder), - show_progress, - build_args.no_timing, - build_args.create_sourcedirs, - &build_args.bsc_path.map(PathBuf::from), - build_args.dev, - build_args.snapshot_output, - ) { - Err(e) => { - println!("{e}"); - std::process::exit(1) - } - Ok(_) => { - if let Some(args_after_build) = build_args.after_build { - cmd::run(args_after_build) - } - std::process::exit(0) - } - }; - } - cli::Command::Watch(watch_args) => { - let filter = watch_args - .filter - .map(|filter| Regex::new(filter.as_ref()).expect("Could not parse regex")); - watcher::start( - &filter, - show_progress, - &args.folder, - watch_args.after_build, - watch_args.create_sourcedirs, - watch_args.dev, - watch_args.bsc_path, - watch_args.snapshot_output, - ); + Ok(()) + } + cli::Command::Clean { + folder, + bsc_path, + snapshot_output, + } => { + let _lock = get_lock(&folder); - Ok(()) - } - cli::Command::CompilerArgs { .. } - | cli::Command::Legacy { .. } - | cli::Command::Format { .. } - | cli::Command::Dump { .. } => { - unreachable!("command already handled") - } - }, + build::clean::clean( + Path::new(&folder as &str), + show_progress, + bsc_path.as_ref().map(PathBuf::from), + *snapshot_output, + ) + } + cli::Command::Legacy { legacy_args } => { + let code = build::pass_through_legacy(legacy_args); + std::process::exit(code); + } + cli::Command::Format { mut format_args } => { + format_args.insert(0, "format".into()); + let code = build::pass_through_legacy(format_args); + std::process::exit(code); + } + cli::Command::Dump { mut dump_args } => { + dump_args.insert(0, "dump".into()); + let code = build::pass_through_legacy(dump_args); + std::process::exit(code); + } + } +} + +fn get_lock(folder: &str) -> lock::Lock { + match lock::get(folder) { + lock::Lock::Error(error) => { + println!("Could not start Rewatch: {error}"); + std::process::exit(1); + } + acquired_lock => acquired_lock, } } diff --git a/rewatch/testrepo/packages/compiled-by-legacy/rescript.json b/rewatch/testrepo/packages/compiled-by-legacy/rescript.json index d62afdf93c..3722c661d5 100644 --- a/rewatch/testrepo/packages/compiled-by-legacy/rescript.json +++ b/rewatch/testrepo/packages/compiled-by-legacy/rescript.json @@ -6,7 +6,7 @@ "subdirs": true }, "package-specs": { - "module": "es6", + "module": "esmodule", "in-source": true }, "suffix": ".res.js" diff --git a/rewatch/tests/legacy.sh b/rewatch/tests/legacy.sh index b3d5c3e029..a5e3de54cb 100755 --- a/rewatch/tests/legacy.sh +++ b/rewatch/tests/legacy.sh @@ -3,19 +3,26 @@ cd ../testrepo/packages/compiled-by-legacy bold "Test: It should use the legacy build system" -error_output=$(rewatch_legacy clean 2>&1 >/dev/null) +error_output=$(rewatch_legacy 2>&1 >/dev/null) +if [ -n "$error_output" ]; +then + error "Error running rewatch" + printf "%s\n" "$error_output" >&2 + exit 1 +fi -if [ $? -eq 0 ]; +error_output=$(rewatch_legacy clean 2>&1 >/dev/null) +file_count=$(find . -name "*.res.js" | wc -l) +if [ $? -eq 0 ] && [ $file_count -eq 0 ]; then success "Test package cleaned" else - error "Error cleaning test package" + error "Error cleaning test package. File count was $file_count." printf "%s\n" "$error_output" >&2 exit 1 fi error_output=$(rewatch_legacy build 2>&1 >/dev/null) - if [ $? -eq 0 ]; then success "Test package built" @@ -32,3 +39,14 @@ else error "Build has changed" exit 1 fi + +error_output=$(rewatch_legacy format -all 2>&1 >/dev/null) +git_diff_file_count=$(git diff --name-only ./ | wc -l) +if [ $? -eq 0 ] && [ $git_diff_file_count -eq 1 ]; +then + success "Test package formatted. Got $git_diff_file_count changed files." +else + error "Error formatting test package" + printf "%s\n" "$error_output" >&2 + exit 1 +fi \ No newline at end of file From f003508b6ee18f0af42f5488e266cfe209092e5a Mon Sep 17 00:00:00 2001 From: Bushuo Date: Sat, 28 Jun 2025 23:32:54 +0200 Subject: [PATCH 17/22] fix: legacy tests inconsistency --- rewatch/tests/legacy.sh | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/rewatch/tests/legacy.sh b/rewatch/tests/legacy.sh index a5e3de54cb..19f80a029b 100755 --- a/rewatch/tests/legacy.sh +++ b/rewatch/tests/legacy.sh @@ -4,9 +4,9 @@ cd ../testrepo/packages/compiled-by-legacy bold "Test: It should use the legacy build system" error_output=$(rewatch_legacy 2>&1 >/dev/null) -if [ -n "$error_output" ]; +if [ $? -ne 0 ]; then - error "Error running rewatch" + error "Error running rewatch legacy" printf "%s\n" "$error_output" >&2 exit 1 fi From c88b2d40fb66821af12f6479cd6b454388084d0e Mon Sep 17 00:00:00 2001 From: Bushuo Date: Sun, 29 Jun 2025 00:11:37 +0200 Subject: [PATCH 18/22] test: is error output printed correctly --- rewatch/tests/legacy.sh | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/rewatch/tests/legacy.sh b/rewatch/tests/legacy.sh index 19f80a029b..3a350c2a3a 100755 --- a/rewatch/tests/legacy.sh +++ b/rewatch/tests/legacy.sh @@ -7,7 +7,7 @@ error_output=$(rewatch_legacy 2>&1 >/dev/null) if [ $? -ne 0 ]; then error "Error running rewatch legacy" - printf "%s\n" "$error_output" >&2 + echo $error_output exit 1 fi @@ -18,7 +18,7 @@ then success "Test package cleaned" else error "Error cleaning test package. File count was $file_count." - printf "%s\n" "$error_output" >&2 + echo $error_output exit 1 fi @@ -28,7 +28,7 @@ then success "Test package built" else error "Error building test package" - printf "%s\n" "$error_output" >&2 + echo $error_output exit 1 fi @@ -47,6 +47,6 @@ then success "Test package formatted. Got $git_diff_file_count changed files." else error "Error formatting test package" - printf "%s\n" "$error_output" >&2 + echo $error_output exit 1 fi \ No newline at end of file From 876b7971fcfa7c8ab038c538583e5f5fb917ca1e Mon Sep 17 00:00:00 2001 From: Bushuo Date: Sun, 29 Jun 2025 00:23:46 +0200 Subject: [PATCH 19/22] debug: print whole output of rewatch legacy --- rewatch/tests/legacy.sh | 1 + 1 file changed, 1 insertion(+) diff --git a/rewatch/tests/legacy.sh b/rewatch/tests/legacy.sh index 3a350c2a3a..6a09359ef7 100755 --- a/rewatch/tests/legacy.sh +++ b/rewatch/tests/legacy.sh @@ -3,6 +3,7 @@ cd ../testrepo/packages/compiled-by-legacy bold "Test: It should use the legacy build system" +rewatch_legacy error_output=$(rewatch_legacy 2>&1 >/dev/null) if [ $? -ne 0 ]; then From 635159bb7527d3d78aed41ce7e34501e5369a131 Mon Sep 17 00:00:00 2001 From: Paul Buschmann Date: Sun, 29 Jun 2025 12:19:44 +0200 Subject: [PATCH 20/22] fix: node script invocation on windows --- rewatch/src/build.rs | 13 ++++++++++--- rewatch/tests/legacy.sh | 1 - 2 files changed, 10 insertions(+), 4 deletions(-) diff --git a/rewatch/src/build.rs b/rewatch/src/build.rs index 50ab16a216..7562872f02 100644 --- a/rewatch/src/build.rs +++ b/rewatch/src/build.rs @@ -554,17 +554,24 @@ pub fn build( } } -pub fn pass_through_legacy(args: Vec) -> i32 { +pub fn pass_through_legacy(mut args: Vec) -> i32 { let project_root = helpers::get_abs_path(Path::new(".")); let workspace_root = helpers::get_workspace_root(&project_root); let rescript_legacy_path = helpers::get_rescript_legacy(&project_root, workspace_root); - let status = std::process::Command::new(rescript_legacy_path) + args.insert(0, rescript_legacy_path.into()); + let status = std::process::Command::new("node") .args(args) .stdout(Stdio::inherit()) .stderr(Stdio::inherit()) .status(); - status.map(|s| s.code().unwrap_or(1)).unwrap_or(1) + match status { + Ok(s) => s.code().unwrap_or(0), + Err(err) => { + eprintln!("Error running the legacy build system: {err}"); + 1 + } + } } diff --git a/rewatch/tests/legacy.sh b/rewatch/tests/legacy.sh index 6a09359ef7..3a350c2a3a 100755 --- a/rewatch/tests/legacy.sh +++ b/rewatch/tests/legacy.sh @@ -3,7 +3,6 @@ cd ../testrepo/packages/compiled-by-legacy bold "Test: It should use the legacy build system" -rewatch_legacy error_output=$(rewatch_legacy 2>&1 >/dev/null) if [ $? -ne 0 ]; then From 2006080116c8341622d6f01f1e3d53383bf0b8b8 Mon Sep 17 00:00:00 2001 From: Paul Buschmann Date: Mon, 30 Jun 2025 15:26:25 +0200 Subject: [PATCH 21/22] Update CHANGELOG.md --- CHANGELOG.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index bd9695b714..6ac6282de1 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -12,6 +12,10 @@ # 12.0.0-alpha.15 (Unreleased) +#### :boom: Breaking Change + +- The legacy rescript cli can be called through rewatch via `rewatch legacy`. Arguments to rewatch need to be passed after the subcommand. https://github.com/rescript-lang/rescript/pull/7551 + #### :bug: Bug fix - Ignore inferred arity in functions inside `%raw` functions, leaving to `%ffi` the responsibility to check the arity since it gives an error in case of mismatch. https://github.com/rescript-lang/rescript/pull/7542 From 834f890546635bc677b8c92dd403a55876b4c9dc Mon Sep 17 00:00:00 2001 From: Paul Buschmann Date: Mon, 30 Jun 2025 16:18:51 +0200 Subject: [PATCH 22/22] Update CHANGELOG.md --- CHANGELOG.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 6ac6282de1..0b52d12ecf 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -14,7 +14,7 @@ #### :boom: Breaking Change -- The legacy rescript cli can be called through rewatch via `rewatch legacy`. Arguments to rewatch need to be passed after the subcommand. https://github.com/rescript-lang/rescript/pull/7551 +- The legacy rescript cli can be called through rewatch via `rewatch legacy`. Arguments to rewatch need to be passed after the subcommand. Argument `--compiler-args` is now a subcommand `compiler-args`. https://github.com/rescript-lang/rescript/pull/7551 #### :bug: Bug fix