diff --git a/cli/emit.rs b/cli/emit.rs index 809260ac0f..337895a105 100644 --- a/cli/emit.rs +++ b/cli/emit.rs @@ -339,7 +339,7 @@ pub fn is_emittable( pub struct CheckOptions { /// The check flag from the option which can effect the filtering of /// diagnostics in the emit result. - pub typecheck_mode: flags::TypecheckMode, + pub type_check_mode: flags::TypeCheckMode, /// Set the debug flag on the TypeScript type checker. pub debug: bool, /// If true, any files emitted will be cached, even if there are diagnostics @@ -430,7 +430,7 @@ pub fn check_and_maybe_emit( root_names, })?; - let diagnostics = if options.typecheck_mode == flags::TypecheckMode::Local { + let diagnostics = if options.type_check_mode == flags::TypeCheckMode::Local { response.diagnostics.filter(|d| { if let Some(file_name) = &d.file_name { !file_name.starts_with("http") diff --git a/cli/flags.rs b/cli/flags.rs index c5c6eea6d2..55d54ab2f5 100644 --- a/cli/flags.rs +++ b/cli/flags.rs @@ -52,6 +52,12 @@ pub struct CacheFlags { pub files: Vec, } +#[derive(Clone, Debug, PartialEq, Deserialize, Serialize)] +pub struct CheckFlags { + pub files: Vec, + pub remote: bool, +} + #[derive(Clone, Debug, PartialEq, Deserialize, Serialize)] pub struct CompileFlags { pub source_file: String, @@ -186,6 +192,7 @@ pub enum DenoSubcommand { Bench(BenchFlags), Bundle(BundleFlags), Cache(CacheFlags), + Check(CheckFlags), Compile(CompileFlags), Completions(CompletionsFlags), Coverage(CoverageFlags), @@ -213,7 +220,7 @@ impl Default for DenoSubcommand { } #[derive(Debug, Clone, PartialEq)] -pub enum TypecheckMode { +pub enum TypeCheckMode { /// Type check all modules. The default value. All, /// Skip type checking of all modules. Represents `--no-check` on the command @@ -224,12 +231,32 @@ pub enum TypecheckMode { Local, } -impl Default for TypecheckMode { +impl Default for TypeCheckMode { fn default() -> Self { Self::All } } +// TODO(bartlomieju): remove once type checking is skipped by default (probably +// in 1.23) +#[derive(Debug, Clone, PartialEq)] +pub enum FutureTypeCheckMode { + /// Type check all modules. The default value. + All, + /// Skip type checking of all modules. Represents `--no-check` on the command + /// line. + None, + /// Only type check local modules. Represents `--no-check=remote` on the + /// command line. + Local, +} + +impl Default for FutureTypeCheckMode { + fn default() -> Self { + Self::None + } +} + #[derive(Clone, Debug, PartialEq, Default)] pub struct Flags { /// Vector of CLI arguments - these are user script arguments, all Deno @@ -252,7 +279,11 @@ pub struct Flags { /// the language server is configured with an explicit cache option. pub cache_path: Option, pub cached_only: bool, - pub typecheck_mode: TypecheckMode, + pub type_check_mode: TypeCheckMode, + // TODO(bartlomieju): should be removed in favor of `check` + // once type checking is skipped by default + pub future_type_check_mode: FutureTypeCheckMode, + pub has_check_flag: bool, pub config_path: Option, pub coverage_dir: Option, pub enable_testing_features: bool, @@ -501,6 +532,7 @@ where Some(("bench", m)) => bench_parse(&mut flags, m), Some(("bundle", m)) => bundle_parse(&mut flags, m), Some(("cache", m)) => cache_parse(&mut flags, m), + Some(("check", m)) => check_parse(&mut flags, m), Some(("compile", m)) => compile_parse(&mut flags, m), Some(("completions", m)) => completions_parse(&mut flags, m, app), Some(("coverage", m)) => coverage_parse(&mut flags, m), @@ -575,6 +607,7 @@ If the flag is set, restrict these messages to errors.", .subcommand(bench_subcommand()) .subcommand(bundle_subcommand()) .subcommand(cache_subcommand()) + .subcommand(check_subcommand()) .subcommand(compile_subcommand()) .subcommand(completions_subcommand()) .subcommand(coverage_subcommand()) @@ -692,6 +725,30 @@ Future runs of this module will trigger no downloads or compilation unless ) } +fn check_subcommand<'a>() -> Command<'a> { + compile_args_without_no_check(Command::new("check")) + .arg( + Arg::new("remote") + .long("remote") + .help("Type-check all modules, including remote") + ) + .arg( + Arg::new("file") + .takes_value(true) + .required(true) + .min_values(1) + .value_hint(ValueHint::FilePath), + ) + .about("Type-check the dependencies") + .long_about( + "Download and type-check without execution. + + deno check https://deno.land/std/http/file_server.ts + +Unless --reload is specified, this command will not re-download already cached dependencies.", + ) +} + fn compile_subcommand<'a>() -> Command<'a> { runtime_args(Command::new("compile"), true, false) .trailing_var_arg(true) @@ -1317,6 +1374,7 @@ fn run_subcommand<'a>() -> Command<'a> { .conflicts_with("inspect-brk"), ) .arg(no_clear_screen_arg()) + .arg(check_arg()) .trailing_var_arg(true) .arg(script_arg().required(true)) .about("Run a JavaScript or TypeScript program") @@ -1610,6 +1668,17 @@ fn compile_args(app: Command) -> Command { .arg(ca_file_arg()) } +fn compile_args_without_no_check(app: Command) -> Command { + app + .arg(import_map_arg()) + .arg(no_remote_arg()) + .arg(config_arg()) + .arg(reload_arg()) + .arg(lock_arg()) + .arg(lock_write_arg()) + .arg(ca_file_arg()) +} + fn permission_args(app: Command) -> Command { app .arg( @@ -1911,6 +1980,25 @@ modules will be ignored.", ) } +fn check_arg<'a>() -> Arg<'a> { + Arg::new("check") + .conflicts_with("no-check") + .long("check") + .takes_value(true) + .require_equals(true) + .min_values(0) + .value_name("CHECK_TYPE") + .help("Type check modules") + .long_help( + "Type check modules. +Currently this is a default behavior to type check modules, but in future releases +Deno will not automatically type check without the --check flag. + +If the value of '--check=all' is supplied, diagnostic errors from remote modules +will be included.", + ) +} + fn script_arg<'a>() -> Arg<'a> { Arg::new("script_arg") .multiple_values(true) @@ -2056,6 +2144,17 @@ fn cache_parse(flags: &mut Flags, matches: &clap::ArgMatches) { flags.subcommand = DenoSubcommand::Cache(CacheFlags { files }); } +fn check_parse(flags: &mut Flags, matches: &clap::ArgMatches) { + compile_args_without_no_check_parse(flags, matches); + let files = matches + .values_of("file") + .unwrap() + .map(String::from) + .collect(); + let remote = matches.is_present("remote"); + flags.subcommand = DenoSubcommand::Check(CheckFlags { files, remote }); +} + fn compile_parse(flags: &mut Flags, matches: &clap::ArgMatches) { runtime_args_parse(flags, matches, true, false); @@ -2342,7 +2441,7 @@ fn lint_parse(flags: &mut Flags, matches: &clap::ArgMatches) { fn repl_parse(flags: &mut Flags, matches: &clap::ArgMatches) { // Use no-check by default for the REPL - flags.typecheck_mode = TypecheckMode::None; + flags.type_check_mode = TypeCheckMode::None; runtime_args_parse(flags, matches, false, true); unsafely_ignore_certificate_errors_parse(flags, matches); handle_repl_flags( @@ -2355,6 +2454,7 @@ fn repl_parse(flags: &mut Flags, matches: &clap::ArgMatches) { fn run_parse(flags: &mut Flags, matches: &clap::ArgMatches) { runtime_args_parse(flags, matches, true, true); + check_arg_parse(flags, matches); let mut script: Vec = matches .values_of("script_arg") @@ -2536,6 +2636,18 @@ fn compile_args_parse(flags: &mut Flags, matches: &clap::ArgMatches) { ca_file_arg_parse(flags, matches); } +fn compile_args_without_no_check_parse( + flags: &mut Flags, + matches: &clap::ArgMatches, +) { + import_map_arg_parse(flags, matches); + no_remote_arg_parse(flags, matches); + config_arg_parse(flags, matches); + reload_arg_parse(flags, matches); + lock_args_parse(flags, matches); + ca_file_arg_parse(flags, matches); +} + fn permission_args_parse(flags: &mut Flags, matches: &clap::ArgMatches) { unsafely_ignore_certificate_errors_parse(flags, matches); if let Some(read_wl) = matches.values_of("allow-read") { @@ -2720,14 +2832,29 @@ fn compat_arg_parse(flags: &mut Flags, matches: &ArgMatches) { fn no_check_arg_parse(flags: &mut Flags, matches: &clap::ArgMatches) { if let Some(cache_type) = matches.value_of("no-check") { match cache_type { - "remote" => flags.typecheck_mode = TypecheckMode::Local, + "remote" => flags.type_check_mode = TypeCheckMode::Local, _ => debug!( "invalid value for 'no-check' of '{}' using default", cache_type ), } } else if matches.is_present("no-check") { - flags.typecheck_mode = TypecheckMode::None; + flags.type_check_mode = TypeCheckMode::None; + } +} + +fn check_arg_parse(flags: &mut Flags, matches: &clap::ArgMatches) { + flags.has_check_flag = matches.is_present("check"); + if let Some(cache_type) = matches.value_of("check") { + match cache_type { + "all" => flags.future_type_check_mode = FutureTypeCheckMode::All, + _ => debug!( + "invalid value for 'check' of '{}' using default", + cache_type + ), + } + } else if matches.is_present("check") { + flags.future_type_check_mode = FutureTypeCheckMode::Local; } } @@ -3500,6 +3627,33 @@ mod tests { ); } + #[test] + fn check() { + let r = flags_from_vec(svec!["deno", "check", "script.ts"]); + assert_eq!( + r.unwrap(), + Flags { + subcommand: DenoSubcommand::Check(CheckFlags { + files: svec!["script.ts"], + remote: false, + }), + ..Flags::default() + } + ); + + let r = flags_from_vec(svec!["deno", "check", "--remote", "script.ts"]); + assert_eq!( + r.unwrap(), + Flags { + subcommand: DenoSubcommand::Check(CheckFlags { + files: svec!["script.ts"], + remote: true, + }), + ..Flags::default() + } + ); + } + #[test] fn info() { let r = flags_from_vec(svec!["deno", "info", "script.ts"]); @@ -3665,7 +3819,7 @@ mod tests { import_map_path: Some("import_map.json".to_string()), no_remote: true, config_path: Some("tsconfig.json".to_string()), - typecheck_mode: TypecheckMode::None, + type_check_mode: TypeCheckMode::None, reload: true, lock: Some(PathBuf::from("lock.json")), lock_write: true, @@ -3750,7 +3904,7 @@ mod tests { import_map_path: Some("import_map.json".to_string()), no_remote: true, config_path: Some("tsconfig.json".to_string()), - typecheck_mode: TypecheckMode::None, + type_check_mode: TypeCheckMode::None, reload: true, lock: Some(PathBuf::from("lock.json")), lock_write: true, @@ -3791,7 +3945,7 @@ mod tests { allow_write: Some(vec![]), allow_ffi: Some(vec![]), allow_hrtime: true, - typecheck_mode: TypecheckMode::None, + type_check_mode: TypeCheckMode::None, ..Flags::default() } ); @@ -4021,7 +4175,7 @@ mod tests { source_file: "script.ts".to_string(), out_file: None, }), - typecheck_mode: TypecheckMode::None, + type_check_mode: TypeCheckMode::None, ..Flags::default() } ); @@ -4243,7 +4397,7 @@ mod tests { import_map_path: Some("import_map.json".to_string()), no_remote: true, config_path: Some("tsconfig.json".to_string()), - typecheck_mode: TypecheckMode::None, + type_check_mode: TypeCheckMode::None, reload: true, lock: Some(PathBuf::from("lock.json")), lock_write: true, @@ -4394,7 +4548,7 @@ mod tests { subcommand: DenoSubcommand::Run(RunFlags { script: "script.ts".to_string(), }), - typecheck_mode: TypecheckMode::None, + type_check_mode: TypeCheckMode::None, ..Flags::default() } ); @@ -4410,7 +4564,7 @@ mod tests { subcommand: DenoSubcommand::Run(RunFlags { script: "script.ts".to_string(), }), - typecheck_mode: TypecheckMode::Local, + type_check_mode: TypeCheckMode::Local, ..Flags::default() } ); @@ -4440,7 +4594,7 @@ mod tests { allow_write: Some(vec![]), allow_ffi: Some(vec![]), allow_hrtime: true, - typecheck_mode: TypecheckMode::None, + type_check_mode: TypeCheckMode::None, ..Flags::default() } ); @@ -4519,7 +4673,7 @@ mod tests { allow_write: Some(vec![]), allow_ffi: Some(vec![]), allow_hrtime: true, - typecheck_mode: TypecheckMode::None, + type_check_mode: TypeCheckMode::None, ..Flags::default() } ); @@ -5084,7 +5238,7 @@ mod tests { import_map_path: Some("import_map.json".to_string()), no_remote: true, config_path: Some("tsconfig.json".to_string()), - typecheck_mode: TypecheckMode::None, + type_check_mode: TypeCheckMode::None, reload: true, lock: Some(PathBuf::from("lock.json")), lock_write: true, @@ -5354,4 +5508,55 @@ mod tests { } ); } + + #[test] + fn run_with_check() { + let r = flags_from_vec(svec!["deno", "run", "--check", "script.ts",]); + assert_eq!( + r.unwrap(), + Flags { + subcommand: DenoSubcommand::Run(RunFlags { + script: "script.ts".to_string(), + }), + future_type_check_mode: FutureTypeCheckMode::Local, + has_check_flag: true, + ..Flags::default() + } + ); + + let r = flags_from_vec(svec!["deno", "run", "--check=all", "script.ts",]); + assert_eq!( + r.unwrap(), + Flags { + subcommand: DenoSubcommand::Run(RunFlags { + script: "script.ts".to_string(), + }), + future_type_check_mode: FutureTypeCheckMode::All, + has_check_flag: true, + ..Flags::default() + } + ); + + let r = flags_from_vec(svec!["deno", "run", "--check=foo", "script.ts",]); + assert_eq!( + r.unwrap(), + Flags { + subcommand: DenoSubcommand::Run(RunFlags { + script: "script.ts".to_string(), + }), + future_type_check_mode: FutureTypeCheckMode::None, + has_check_flag: true, + ..Flags::default() + } + ); + + let r = flags_from_vec(svec![ + "deno", + "run", + "--no-check", + "--check", + "script.ts", + ]); + assert!(r.is_err()); + } } diff --git a/cli/main.rs b/cli/main.rs index 0435775ad1..689d5c6342 100644 --- a/cli/main.rs +++ b/cli/main.rs @@ -43,6 +43,7 @@ use crate::file_watcher::ResolutionResult; use crate::flags::BenchFlags; use crate::flags::BundleFlags; use crate::flags::CacheFlags; +use crate::flags::CheckFlags; use crate::flags::CompileFlags; use crate::flags::CompletionsFlags; use crate::flags::CoverageFlags; @@ -51,6 +52,7 @@ use crate::flags::DocFlags; use crate::flags::EvalFlags; use crate::flags::Flags; use crate::flags::FmtFlags; +use crate::flags::FutureTypeCheckMode; use crate::flags::InfoFlags; use crate::flags::InstallFlags; use crate::flags::LintFlags; @@ -58,7 +60,7 @@ use crate::flags::ReplFlags; use crate::flags::RunFlags; use crate::flags::TaskFlags; use crate::flags::TestFlags; -use crate::flags::TypecheckMode; +use crate::flags::TypeCheckMode; use crate::flags::UninstallFlags; use crate::flags::UpgradeFlags; use crate::flags::VendorFlags; @@ -585,6 +587,31 @@ async fn cache_command( Ok(0) } +async fn check_command( + flags: Flags, + check_flags: CheckFlags, +) -> Result { + // NOTE(bartlomieju): currently just an alias for `deno cache`, but + // it will be changed in Deno 2.0. + let mut flags = flags.clone(); + + // In `deno check` the default mode is to check only + // local modules, with `--remote` we check remote modules too. + flags.type_check_mode = if check_flags.remote { + TypeCheckMode::All + } else { + TypeCheckMode::Local + }; + + cache_command( + flags, + CacheFlags { + files: check_flags.files, + }, + ) + .await +} + async fn eval_command( flags: Flags, eval_flags: EvalFlags, @@ -679,12 +706,12 @@ async fn create_graph_and_maybe_check( .unwrap_or(false); graph_valid( &graph, - ps.flags.typecheck_mode != TypecheckMode::None, + ps.flags.type_check_mode != TypeCheckMode::None, check_js, )?; graph_lock_or_exit(&graph); - if ps.flags.typecheck_mode != TypecheckMode::None { + if ps.flags.type_check_mode != TypeCheckMode::None { let lib = if ps.flags.unstable { emit::TypeLib::UnstableDenoWindow } else { @@ -708,7 +735,7 @@ async fn create_graph_and_maybe_check( Arc::new(RwLock::new(graph.as_ref().into())), &mut cache, emit::CheckOptions { - typecheck_mode: ps.flags.typecheck_mode.clone(), + type_check_mode: ps.flags.type_check_mode.clone(), debug, emit_with_diagnostics: false, maybe_config_specifier, @@ -739,7 +766,7 @@ fn bundle_module_graph( ps.maybe_config_file.as_ref(), None, )?; - if flags.typecheck_mode == TypecheckMode::None { + if flags.type_check_mode == TypeCheckMode::None { if let Some(ignored_options) = maybe_ignored_options { eprintln!("{}", ignored_options); } @@ -1010,7 +1037,7 @@ async fn run_with_watch(flags: Flags, script: String) -> Result { .unwrap_or(false); graph_valid( &graph, - ps.flags.typecheck_mode != flags::TypecheckMode::None, + ps.flags.type_check_mode != flags::TypeCheckMode::None, check_js, )?; @@ -1140,6 +1167,11 @@ async fn run_command( flags: Flags, run_flags: RunFlags, ) -> Result { + if !flags.has_check_flag && flags.type_check_mode == TypeCheckMode::All { + info!("{} In future releases `deno run` will not automatically type check without the --check flag. +To opt into this new behavior now, specify DENO_FUTURE_CHECK=1.", colors::yellow("Warning")); + } + // Read script content from stdin if run_flags.script == "-" { return run_from_stdin(flags).await; @@ -1349,6 +1381,9 @@ fn get_subcommand( DenoSubcommand::Cache(cache_flags) => { cache_command(flags, cache_flags).boxed_local() } + DenoSubcommand::Check(check_flags) => { + check_command(flags, check_flags).boxed_local() + } DenoSubcommand::Compile(compile_flags) => { compile_command(flags, compile_flags).boxed_local() } @@ -1458,7 +1493,7 @@ pub fn main() { // TODO(bartlomieju): doesn't handle exit code set by the runtime properly unwrap_or_exit(standalone_res); - let flags = match flags::flags_from_vec(args) { + let mut flags = match flags::flags_from_vec(args) { Ok(flags) => flags, Err(err @ clap::Error { .. }) if err.kind() == clap::ErrorKind::DisplayHelp @@ -1475,6 +1510,21 @@ pub fn main() { logger::init(flags.log_level); + // TODO(bartlomieju): remove once type checking is skipped by default (probably + // in 1.23). + // If this env var is set we're gonna override default behavior of type checking + // and use behavior defined by the `--check` flag. + let future_check_env_var = env::var("DENO_FUTURE_CHECK").ok(); + if let Some(env_var) = future_check_env_var { + if env_var == "1" { + flags.type_check_mode = match &flags.future_type_check_mode { + FutureTypeCheckMode::None => TypeCheckMode::None, + FutureTypeCheckMode::All => TypeCheckMode::All, + FutureTypeCheckMode::Local => TypeCheckMode::Local, + } + } + } + let exit_code = get_subcommand(flags).await; exit_code diff --git a/cli/ops/runtime_compiler.rs b/cli/ops/runtime_compiler.rs index 372d534682..feed07a1c6 100644 --- a/cli/ops/runtime_compiler.rs +++ b/cli/ops/runtime_compiler.rs @@ -245,7 +245,7 @@ async fn op_emit( Arc::new(RwLock::new(graph.as_ref().into())), cache.as_mut_cacher(), emit::CheckOptions { - typecheck_mode: flags::TypecheckMode::All, + type_check_mode: flags::TypeCheckMode::All, debug, emit_with_diagnostics: true, maybe_config_specifier: None, @@ -268,7 +268,7 @@ async fn op_emit( Arc::new(RwLock::new(graph.as_ref().into())), cache.as_mut_cacher(), emit::CheckOptions { - typecheck_mode: flags::TypecheckMode::All, + type_check_mode: flags::TypeCheckMode::All, debug, emit_with_diagnostics: true, maybe_config_specifier: None, diff --git a/cli/proc_state.rs b/cli/proc_state.rs index f01d0bc2d2..fc132dadcd 100644 --- a/cli/proc_state.rs +++ b/cli/proc_state.rs @@ -304,12 +304,12 @@ impl ProcState { }; if !reload_on_watch { let graph_data = self.graph_data.read(); - if self.flags.typecheck_mode == flags::TypecheckMode::None + if self.flags.type_check_mode == flags::TypeCheckMode::None || graph_data.is_type_checked(&roots, &lib) { if let Some(result) = graph_data.check( &roots, - self.flags.typecheck_mode != flags::TypecheckMode::None, + self.flags.type_check_mode != flags::TypeCheckMode::None, false, ) { return result; @@ -419,21 +419,21 @@ impl ProcState { graph_data .check( &roots, - self.flags.typecheck_mode != flags::TypecheckMode::None, + self.flags.type_check_mode != flags::TypeCheckMode::None, check_js, ) .unwrap()?; } - let config_type = if self.flags.typecheck_mode == flags::TypecheckMode::None - { - emit::ConfigType::Emit - } else { - emit::ConfigType::Check { - tsc_emit: true, - lib: lib.clone(), - } - }; + let config_type = + if self.flags.type_check_mode == flags::TypeCheckMode::None { + emit::ConfigType::Emit + } else { + emit::ConfigType::Check { + tsc_emit: true, + lib: lib.clone(), + } + }; let (ts_config, maybe_ignored_options) = emit::get_ts_config(config_type, self.maybe_config_file.as_ref(), None)?; @@ -442,7 +442,7 @@ impl ProcState { log::warn!("{}", ignored_options); } - if self.flags.typecheck_mode == flags::TypecheckMode::None { + if self.flags.type_check_mode == flags::TypeCheckMode::None { let options = emit::EmitOptions { ts_config, reload: self.flags.reload, @@ -456,7 +456,7 @@ impl ProcState { .as_ref() .map(|cf| cf.specifier.clone()); let options = emit::CheckOptions { - typecheck_mode: self.flags.typecheck_mode.clone(), + type_check_mode: self.flags.type_check_mode.clone(), debug: self.flags.log_level == Some(log::Level::Debug), emit_with_diagnostics: false, maybe_config_specifier, @@ -477,7 +477,7 @@ impl ProcState { log::debug!("{}", emit_result.stats); } - if self.flags.typecheck_mode != flags::TypecheckMode::None { + if self.flags.type_check_mode != flags::TypeCheckMode::None { let mut graph_data = self.graph_data.write(); graph_data.set_type_checked(&roots, &lib); } diff --git a/cli/tests/integration/bundle_tests.rs b/cli/tests/integration/bundle_tests.rs index bb2489e03a..e1a75f18d5 100644 --- a/cli/tests/integration/bundle_tests.rs +++ b/cli/tests/integration/bundle_tests.rs @@ -34,6 +34,7 @@ fn bundle_exports() { let output = util::deno_cmd() .current_dir(util::testdata_path()) + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(&test) .output() @@ -56,7 +57,6 @@ fn bundle_exports_no_check() { let mut deno = util::deno_cmd() .current_dir(util::testdata_path()) .arg("bundle") - .arg("--no-check") .arg(mod1) .arg(&bundle) .spawn() @@ -77,6 +77,7 @@ fn bundle_exports_no_check() { let output = util::deno_cmd() .current_dir(util::testdata_path()) + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(&test) .output() @@ -109,6 +110,7 @@ fn bundle_circular() { let output = util::deno_cmd() .current_dir(util::testdata_path()) + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(&bundle) .output() @@ -141,6 +143,7 @@ fn bundle_single_module() { let output = util::deno_cmd() .current_dir(util::testdata_path()) + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(&bundle) .output() @@ -183,6 +186,7 @@ fn bundle_tla() { let output = util::deno_cmd() .current_dir(util::testdata_path()) + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(&test) .output() @@ -215,6 +219,7 @@ fn bundle_js() { let output = util::deno_cmd() .current_dir(util::testdata_path()) + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(&bundle) .output() @@ -289,7 +294,9 @@ fn bundle_import_map() { let output = util::deno_cmd() .current_dir(util::testdata_path()) + .env("DENO_FUTURE_CHECK", "1") .arg("run") + .arg("--check") .arg(&test) .output() .unwrap(); @@ -311,7 +318,6 @@ fn bundle_import_map_no_check() { let mut deno = util::deno_cmd() .current_dir(util::testdata_path()) .arg("bundle") - .arg("--no-check") .arg("--import-map") .arg(import_map_path) .arg(import) @@ -334,6 +340,7 @@ fn bundle_import_map_no_check() { let output = util::deno_cmd() .current_dir(util::testdata_path()) + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(&test) .output() @@ -366,6 +373,7 @@ fn bundle_json_module() { let output = util::deno_cmd() .current_dir(util::testdata_path()) + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(&bundle) .output() @@ -398,6 +406,7 @@ fn bundle_json_module_escape_sub() { let output = util::deno_cmd() .current_dir(util::testdata_path()) + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(&bundle) .output() diff --git a/cli/tests/integration/check_tests.rs b/cli/tests/integration/check_tests.rs new file mode 100644 index 0000000000..f605a733a3 --- /dev/null +++ b/cli/tests/integration/check_tests.rs @@ -0,0 +1,34 @@ +// Copyright 2018-2022 the Deno authors. All rights reserved. MIT license. + +use crate::itest; + +itest!(_095_check_with_bare_import { + args: "check 095_cache_with_bare_import.ts", + output: "095_cache_with_bare_import.ts.out", + exit_code: 1, +}); + +itest!(check_extensionless { + args: "check --reload http://localhost:4545/subdir/no_js_ext", + output: "cache_extensionless.out", + http_server: true, +}); + +itest!(check_random_extension { + args: "check --reload http://localhost:4545/subdir/no_js_ext@1.0.0", + output: "cache_random_extension.out", + http_server: true, +}); + +itest!(check_all { + args: "check --quiet --remote check_all.ts", + output: "check_all.out", + http_server: true, + exit_code: 1, +}); + +itest!(check_all_local { + args: "check --quiet check_all.ts", + output_str: Some(""), + http_server: true, +}); diff --git a/cli/tests/integration/inspector_tests.rs b/cli/tests/integration/inspector_tests.rs index 71ecaf22ee..86a5d42642 100644 --- a/cli/tests/integration/inspector_tests.rs +++ b/cli/tests/integration/inspector_tests.rs @@ -142,6 +142,7 @@ async fn assert_inspector_messages( async fn inspector_connect() { let script = util::testdata_path().join("inspector/inspector1.js"); let mut child = util::deno_cmd() + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(inspect_flag_with_unique_port("--inspect")) .arg(script) @@ -167,6 +168,7 @@ async fn inspector_connect() { async fn inspector_break_on_first_line() { let script = util::testdata_path().join("inspector/inspector2.js"); let mut child = util::deno_cmd() + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(inspect_flag_with_unique_port("--inspect-brk")) .arg(script) @@ -257,6 +259,7 @@ async fn inspector_break_on_first_line() { async fn inspector_pause() { let script = util::testdata_path().join("inspector/inspector1.js"); let mut child = util::deno_cmd() + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(inspect_flag_with_unique_port("--inspect")) .arg(script) @@ -327,6 +330,7 @@ async fn inspector_port_collision() { let inspect_flag = inspect_flag_with_unique_port("--inspect"); let mut child1 = util::deno_cmd() + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(&inspect_flag) .arg(script.clone()) @@ -341,6 +345,7 @@ async fn inspector_port_collision() { let _ = extract_ws_url_from_stderr(&mut stderr_1_lines); let mut child2 = util::deno_cmd() + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(&inspect_flag) .arg(script) @@ -365,6 +370,7 @@ async fn inspector_port_collision() { async fn inspector_does_not_hang() { let script = util::testdata_path().join("inspector/inspector3.js"); let mut child = util::deno_cmd() + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(inspect_flag_with_unique_port("--inspect-brk")) .env("NO_COLOR", "1") @@ -476,6 +482,7 @@ async fn inspector_does_not_hang() { async fn inspector_without_brk_runs_code() { let script = util::testdata_path().join("inspector/inspector4.js"); let mut child = util::deno_cmd() + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(inspect_flag_with_unique_port("--inspect")) .arg(script) @@ -603,6 +610,7 @@ async fn inspector_runtime_evaluate_does_not_crash() { async fn inspector_json() { let script = util::testdata_path().join("inspector/inspector1.js"); let mut child = util::deno_cmd() + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(inspect_flag_with_unique_port("--inspect")) .arg(script) @@ -632,6 +640,7 @@ async fn inspector_json() { async fn inspector_json_list() { let script = util::testdata_path().join("inspector/inspector1.js"); let mut child = util::deno_cmd() + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(inspect_flag_with_unique_port("--inspect")) .arg(script) @@ -663,6 +672,7 @@ async fn inspector_connect_non_ws() { // Verify we don't panic if non-WS connection is being established let script = util::testdata_path().join("inspector/inspector1.js"); let mut child = util::deno_cmd() + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(inspect_flag_with_unique_port("--inspect")) .arg(script) @@ -688,6 +698,7 @@ async fn inspector_connect_non_ws() { async fn inspector_break_on_first_line_in_test() { let script = util::testdata_path().join("inspector/inspector_test.js"); let mut child = util::deno_cmd() + .env("DENO_FUTURE_CHECK", "1") .arg("test") .arg(inspect_flag_with_unique_port("--inspect-brk")) .arg(script) @@ -782,7 +793,9 @@ async fn inspector_break_on_first_line_in_test() { async fn inspector_with_ts_files() { let script = util::testdata_path().join("inspector/test.ts"); let mut child = util::deno_cmd() + .env("DENO_FUTURE_CHECK", "1") .arg("run") + .arg("--check") .arg(inspect_flag_with_unique_port("--inspect-brk")) .arg(script) .stdout(std::process::Stdio::piped()) @@ -907,6 +920,7 @@ async fn inspector_with_ts_files() { async fn inspector_memory() { let script = util::testdata_path().join("inspector/memory.js"); let mut child = util::deno_cmd() + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(inspect_flag_with_unique_port("--inspect-brk")) .arg(script) @@ -1021,6 +1035,7 @@ async fn inspector_memory() { async fn inspector_profile() { let script = util::testdata_path().join("inspector/memory.js"); let mut child = util::deno_cmd() + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg(inspect_flag_with_unique_port("--inspect-brk")) .arg(script) diff --git a/cli/tests/integration/mod.rs b/cli/tests/integration/mod.rs index 86a980f594..2578989c7a 100644 --- a/cli/tests/integration/mod.rs +++ b/cli/tests/integration/mod.rs @@ -56,6 +56,8 @@ mod bench; mod bundle; #[path = "cache_tests.rs"] mod cache; +#[path = "check_tests.rs"] +mod check; #[path = "compat_tests.rs"] mod compat; #[path = "compile_tests.rs"] @@ -293,7 +295,9 @@ fn ts_dependency_recompilation() { let output = util::deno_cmd() .current_dir(util::testdata_path()) .env("NO_COLOR", "1") + .env("DENO_FUTURE_CHECK", "1") .arg("run") + .arg("--check") .arg(&ats) .output() .expect("failed to spawn script"); @@ -315,7 +319,9 @@ fn ts_dependency_recompilation() { let output = util::deno_cmd() .current_dir(util::testdata_path()) .env("NO_COLOR", "1") + .env("DENO_FUTURE_CHECK", "1") .arg("run") + .arg("--check") .arg(&ats) .output() .expect("failed to spawn script"); @@ -338,9 +344,11 @@ fn ts_no_recheck_on_redirect() { assert!(redirect_ts.is_file()); let mut cmd = Command::new(e.clone()); cmd.env("DENO_DIR", deno_dir.path()); + cmd.env("DENO_FUTURE_CHECK", "1"); let mut initial = cmd .current_dir(util::testdata_path()) .arg("run") + .arg("--check") .arg(redirect_ts.clone()) .spawn() .expect("failed to span script"); @@ -350,9 +358,11 @@ fn ts_no_recheck_on_redirect() { let mut cmd = Command::new(e); cmd.env("DENO_DIR", deno_dir.path()); + cmd.env("DENO_FUTURE_CHECK", "1"); let output = cmd .current_dir(util::testdata_path()) .arg("run") + .arg("--check") .arg(redirect_ts) .output() .expect("failed to spawn script"); @@ -652,7 +662,9 @@ fn cafile_bundle_remote_exports() { let output = util::deno_cmd() .current_dir(util::testdata_path()) + .env("DENO_FUTURE_CHECK", "1") .arg("run") + .arg("--check") .arg(&test) .output() .expect("failed to spawn script"); @@ -975,7 +987,9 @@ async fn test_resolve_dns() { let output = util::deno_cmd() .current_dir(util::testdata_path()) .env("NO_COLOR", "1") + .env("DENO_FUTURE_CHECK", "1") .arg("run") + .arg("--check") .arg("--allow-net") .arg("resolve_dns.ts") .stdout(std::process::Stdio::piped()) @@ -1000,7 +1014,9 @@ async fn test_resolve_dns() { let output = util::deno_cmd() .current_dir(util::testdata_path()) .env("NO_COLOR", "1") + .env("DENO_FUTURE_CHECK", "1") .arg("run") + .arg("--check") .arg("--allow-net=127.0.0.1:4553") .arg("resolve_dns.ts") .stdout(std::process::Stdio::piped()) @@ -1025,7 +1041,9 @@ async fn test_resolve_dns() { let output = util::deno_cmd() .current_dir(util::testdata_path()) .env("NO_COLOR", "1") + .env("DENO_FUTURE_CHECK", "1") .arg("run") + .arg("--check") .arg("--allow-net=deno.land") .arg("resolve_dns.ts") .stdout(std::process::Stdio::piped()) @@ -1047,7 +1065,9 @@ async fn test_resolve_dns() { let output = util::deno_cmd() .current_dir(util::testdata_path()) .env("NO_COLOR", "1") + .env("DENO_FUTURE_CHECK", "1") .arg("run") + .arg("--check") .arg("resolve_dns.ts") .stdout(std::process::Stdio::piped()) .stderr(std::process::Stdio::piped()) diff --git a/cli/tests/integration/run_tests.rs b/cli/tests/integration/run_tests.rs index 43a7612049..a56e3f0f15 100644 --- a/cli/tests/integration/run_tests.rs +++ b/cli/tests/integration/run_tests.rs @@ -13,6 +13,7 @@ itest!(stdout_write_all { itest!(_001_hello { args: "run --reload 001_hello.js", output: "001_hello.js.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(_002_hello { @@ -104,8 +105,9 @@ itest!(_021_mjs_modules { }); itest!(_023_no_ext { - args: "run --reload 023_no_ext", + args: "run --reload --check 023_no_ext", output: "023_no_ext.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); // TODO(lucacasonato): remove --unstable when permissions goes stable @@ -155,10 +157,11 @@ itest!(_034_onload { }); itest!(_035_cached_only_flag { - args: "run --reload --cached-only http://127.0.0.1:4545/019_media_types.ts", + args: "run --reload --check --cached-only http://127.0.0.1:4545/019_media_types.ts", output: "035_cached_only_flag.out", exit_code: 1, http_server: true, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(_038_checkjs { @@ -202,10 +205,12 @@ itest!(_048_media_types_jsx { }); itest!(_052_no_remote_flag { - args: "run --reload --no-remote http://127.0.0.1:4545/019_media_types.ts", + args: + "run --reload --check --no-remote http://127.0.0.1:4545/019_media_types.ts", output: "052_no_remote_flag.out", exit_code: 1, http_server: true, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(_056_make_temp_file_write_perm { @@ -552,6 +557,7 @@ itest!(blob_gc_finalization { args: "run blob_gc_finalization.js", output: "blob_gc_finalization.js.out", exit_code: 0, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(fetch_response_finalization { @@ -559,6 +565,7 @@ itest!(fetch_response_finalization { output: "fetch_response_finalization.js.out", http_server: true, exit_code: 0, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(import_type { @@ -664,8 +671,9 @@ itest!(config_types_remote { }); itest!(empty_typescript { - args: "run --reload subdir/empty.ts", + args: "run --reload --check subdir/empty.ts", output_str: Some("Check file:[WILDCARD]/subdir/empty.ts\n"), + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(error_001 { @@ -739,20 +747,23 @@ itest!(error_011_bad_module_specifier { }); itest!(error_012_bad_dynamic_import_specifier { - args: "run --reload error_012_bad_dynamic_import_specifier.ts", + args: "run --reload --check error_012_bad_dynamic_import_specifier.ts", exit_code: 1, output: "error_012_bad_dynamic_import_specifier.ts.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(error_013_missing_script { args: "run --reload missing_file_name", exit_code: 1, output: "error_013_missing_script.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(error_014_catch_dynamic_import_error { args: "run --reload --allow-read error_014_catch_dynamic_import_error.js", output: "error_014_catch_dynamic_import_error.js.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(error_015_dynamic_import_permissions { @@ -780,6 +791,7 @@ itest!(error_018_hide_long_source_js { args: "run error_018_hide_long_source_js.js", output: "error_018_hide_long_source_js.js.out", exit_code: 1, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(error_019_stack_function { @@ -853,12 +865,14 @@ itest!(error_syntax { args: "run --reload error_syntax.js", exit_code: 1, output: "error_syntax.js.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(error_syntax_empty_trailing_line { args: "run --reload error_syntax_empty_trailing_line.mjs", exit_code: 1, output: "error_syntax_empty_trailing_line.mjs.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(error_type_definitions { @@ -989,8 +1003,8 @@ itest!(lib_runtime_api { itest!(seed_random { args: "run --seed=100 seed_random.js", - output: "seed_random.js.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(type_definitions { @@ -999,9 +1013,10 @@ itest!(type_definitions { }); itest!(type_definitions_for_export { - args: "run --reload type_definitions_for_export.ts", + args: "run --reload --check type_definitions_for_export.ts", output: "type_definitions_for_export.ts.out", exit_code: 1, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(type_directives_01 { @@ -1022,37 +1037,43 @@ itest!(type_directives_js_main { }); itest!(type_directives_redirect { - args: "run --reload type_directives_redirect.ts", + args: "run --reload --check type_directives_redirect.ts", output: "type_directives_redirect.ts.out", http_server: true, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(type_headers_deno_types { - args: "run --reload type_headers_deno_types.ts", + args: "run --reload --check type_headers_deno_types.ts", output: "type_headers_deno_types.ts.out", http_server: true, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(ts_type_imports { - args: "run --reload ts_type_imports.ts", + args: "run --reload --check ts_type_imports.ts", output: "ts_type_imports.ts.out", exit_code: 1, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(ts_decorators { - args: "run --reload -c tsconfig.decorators.json ts_decorators.ts", + args: "run --reload -c tsconfig.decorators.json --check ts_decorators.ts", output: "ts_decorators.ts.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(ts_type_only_import { - args: "run --reload ts_type_only_import.ts", + args: "run --reload --check ts_type_only_import.ts", output: "ts_type_only_import.ts.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(swc_syntax_error { - args: "run --reload swc_syntax_error.ts", + args: "run --reload --check swc_syntax_error.ts", output: "swc_syntax_error.ts.out", exit_code: 1, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unbuffered_stderr { @@ -1068,6 +1089,7 @@ itest!(unbuffered_stdout { itest!(v8_flags_run { args: "run --v8-flags=--expose-gc v8_flags.js", output: "v8_flags.js.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(v8_flags_unrecognized { @@ -1100,12 +1122,14 @@ itest!(wasm_shared { itest!(wasm_async { args: "run wasm_async.js", output: "wasm_async.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(wasm_unreachable { args: "run --allow-read wasm_unreachable.js", output: "wasm_unreachable.out", exit_code: 1, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(wasm_url { @@ -1123,34 +1147,40 @@ itest!(weakref { itest!(top_level_await_order { args: "run --allow-read top_level_await_order.js", output: "top_level_await_order.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(top_level_await_loop { args: "run --allow-read top_level_await_loop.js", output: "top_level_await_loop.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(top_level_await_circular { args: "run --allow-read top_level_await_circular.js", output: "top_level_await_circular.out", exit_code: 1, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); // Regression test for https://github.com/denoland/deno/issues/11238. itest!(top_level_await_nested { args: "run --allow-read top_level_await_nested/main.js", output: "top_level_await_nested.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(top_level_await_unresolved { args: "run top_level_await_unresolved.js", output: "top_level_await_unresolved.out", exit_code: 1, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(top_level_await { args: "run --allow-read top_level_await.js", output: "top_level_await.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(top_level_await_ts { @@ -1182,6 +1212,7 @@ itest!(unstable_enabled { itest!(unstable_disabled_js { args: "run --reload unstable.js", output: "unstable_disabled_js.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unstable_enabled_js { @@ -1220,13 +1251,15 @@ itest!(dynamic_import_conditional { }); itest!(tsx_imports { - args: "run --reload tsx_imports.ts", + args: "run --reload --check tsx_imports.ts", output: "tsx_imports.ts.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(fix_dynamic_import_errors { args: "run --reload fix_dynamic_import_errors.js", output: "fix_dynamic_import_errors.js.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(fix_emittable_skipped { @@ -1401,6 +1434,7 @@ itest!(jsx_import_source_import_map_no_check { itest!(proto_exploit { args: "run proto_exploit.js", output: "proto_exploit.js.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(reference_types { @@ -1497,6 +1531,7 @@ itest!(classic_workers_event_loop { args: "run --enable-testing-features-do-not-use classic_workers_event_loop.js", output: "classic_workers_event_loop.js.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); // FIXME(bartlomieju): disabled, because this test is very flaky on CI @@ -1548,6 +1583,7 @@ itest!(error_import_map_unable_to_load { args: "run --import-map=import_maps/does_not_exist.json import_maps/test.ts", output: "error_import_map_unable_to_load.out", exit_code: 1, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); // Test that setting `self` in the main thread to some other value doesn't break @@ -1555,6 +1591,7 @@ itest!(error_import_map_unable_to_load { itest!(replace_self { args: "run replace_self.js", output: "replace_self.js.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(worker_event_handler_test { @@ -1589,9 +1626,10 @@ itest!(worker_close_in_wasm_reactions { }); itest!(reference_types_error { - args: "run --config checkjs.tsconfig.json reference_types_error.js", + args: "run --config checkjs.tsconfig.json --check reference_types_error.js", output: "reference_types_error.js.out", exit_code: 1, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(reference_types_error_no_check { @@ -1600,9 +1638,10 @@ itest!(reference_types_error_no_check { }); itest!(jsx_import_source_error { - args: "run --config jsx/deno-jsx-error.jsonc jsx_import_source_no_pragma.tsx", + args: "run --config jsx/deno-jsx-error.jsonc --check jsx_import_source_no_pragma.tsx", output: "jsx_import_source_error.out", exit_code: 1, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(shebang_tsc { @@ -1631,6 +1670,7 @@ itest!(shebang_with_json_imports_swc { fn no_validate_asm() { let output = util::deno_cmd() .current_dir(util::testdata_path()) + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg("no_validate_asm.js") .stderr(std::process::Stdio::piped()) @@ -1775,6 +1815,7 @@ fn rust_log() { // Without RUST_LOG the stderr is empty. let output = util::deno_cmd() .current_dir(util::testdata_path()) + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg("001_hello.js") .stderr(std::process::Stdio::piped()) @@ -1788,6 +1829,7 @@ fn rust_log() { // With RUST_LOG the stderr is not empty. let output = util::deno_cmd() .current_dir(util::testdata_path()) + .env("DENO_FUTURE_CHECK", "1") .arg("run") .arg("001_hello.js") .env("RUST_LOG", "debug") @@ -2362,6 +2404,7 @@ itest!(eval_context_throw_with_conflicting_source { itest!(eval_context_throw_dom_exception { args: "run eval_context_throw_dom_exception.js", output: "eval_context_throw_dom_exception.js.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); #[test] @@ -2493,11 +2536,13 @@ itest!(import_assertions_type_check { itest!(delete_window { args: "run delete_window.js", output_str: Some("true\n"), + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(colors_without_global_this { args: "run colors_without_globalThis.js", output_str: Some("true\n"), + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(config_auto_discovered_for_local_script { @@ -2515,6 +2560,7 @@ itest!(wasm_streaming_panic_test { args: "run wasm_streaming_panic_test.js", output: "wasm_streaming_panic_test.js.out", exit_code: 1, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); // Regression test for https://github.com/denoland/deno/issues/13897. @@ -2528,88 +2574,114 @@ itest!(unstable_ffi_1 { args: "run unstable_ffi_1.js", output: "unstable_ffi_1.js.out", exit_code: 70, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unstable_ffi_2 { args: "run unstable_ffi_2.js", output: "unstable_ffi_2.js.out", exit_code: 70, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unstable_ffi_3 { args: "run unstable_ffi_3.js", output: "unstable_ffi_3.js.out", exit_code: 70, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unstable_ffi_4 { args: "run unstable_ffi_4.js", output: "unstable_ffi_4.js.out", exit_code: 70, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unstable_ffi_5 { args: "run unstable_ffi_5.js", output: "unstable_ffi_5.js.out", exit_code: 70, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unstable_ffi_6 { args: "run unstable_ffi_6.js", output: "unstable_ffi_6.js.out", exit_code: 70, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unstable_ffi_7 { args: "run unstable_ffi_7.js", output: "unstable_ffi_7.js.out", exit_code: 70, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unstable_ffi_8 { args: "run unstable_ffi_8.js", output: "unstable_ffi_8.js.out", exit_code: 70, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unstable_ffi_9 { args: "run unstable_ffi_9.js", output: "unstable_ffi_9.js.out", exit_code: 70, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unstable_ffi_10 { args: "run unstable_ffi_10.js", output: "unstable_ffi_10.js.out", exit_code: 70, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unstable_ffi_11 { args: "run unstable_ffi_11.js", output: "unstable_ffi_11.js.out", exit_code: 70, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unstable_ffi_12 { args: "run unstable_ffi_12.js", output: "unstable_ffi_12.js.out", exit_code: 70, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unstable_ffi_13 { args: "run unstable_ffi_13.js", output: "unstable_ffi_13.js.out", exit_code: 70, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unstable_ffi_14 { args: "run unstable_ffi_14.js", output: "unstable_ffi_14.js.out", exit_code: 70, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); itest!(unstable_ffi_15 { args: "run unstable_ffi_15.js", output: "unstable_ffi_15.js.out", exit_code: 70, + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], +}); + +itest!(future_check1 { + args: "run future_check.ts", + output: "future_check1.out", +}); + +itest!(future_check2 { + args: "run --check future_check.ts", + output: "future_check2.out", + envs: vec![("DENO_FUTURE_CHECK".to_string(), "1".to_string())], }); diff --git a/cli/tests/integration/watcher_tests.rs b/cli/tests/integration/watcher_tests.rs index 2f2bc98517..939a11c0c9 100644 --- a/cli/tests/integration/watcher_tests.rs +++ b/cli/tests/integration/watcher_tests.rs @@ -633,6 +633,7 @@ fn run_watch_load_unload_events() { .arg("--unstable") .arg(&file_to_watch) .env("NO_COLOR", "1") + .env("DENO_FUTURE_CHECK", "1") .stdout(std::process::Stdio::piped()) .stderr(std::process::Stdio::piped()) .spawn() @@ -688,6 +689,7 @@ fn run_watch_not_exit() { .arg("--unstable") .arg(&file_to_watch) .env("NO_COLOR", "1") + .env("DENO_FUTURE_CHECK", "1") .stdout(std::process::Stdio::piped()) .stderr(std::process::Stdio::piped()) .spawn() @@ -748,6 +750,7 @@ fn run_watch_with_import_map_and_relative_paths() { .arg(&import_map_path) .arg(&file_to_watch) .env("NO_COLOR", "1") + .env("DENO_FUTURE_CHECK", "1") .stdout(std::process::Stdio::piped()) .stderr(std::process::Stdio::piped()) .spawn() @@ -971,6 +974,7 @@ fn test_watch_module_graph_error_referrer() { .arg("--unstable") .arg(&file_to_watch) .env("NO_COLOR", "1") + .env("DENO_FUTURE_CHECK", "1") .stdout(std::process::Stdio::piped()) .stderr(std::process::Stdio::piped()) .spawn() @@ -1004,6 +1008,7 @@ fn watch_with_no_clear_screen_flag() { .arg("--unstable") .arg(&file_to_watch) .env("NO_COLOR", "1") + .env("DENO_FUTURE_CHECK", "1") .stdout(std::process::Stdio::piped()) .stderr(std::process::Stdio::piped()) .spawn() diff --git a/cli/tests/testdata/check_all.out b/cli/tests/testdata/check_all.out new file mode 100644 index 0000000000..3442646348 --- /dev/null +++ b/cli/tests/testdata/check_all.out @@ -0,0 +1,4 @@ +error: TS2322 [ERROR]: Type '12' is not assignable to type '"a"'. +export const a: "a" = 12; + ^ + at http://localhost:4545/subdir/type_error.ts:1:14 diff --git a/cli/tests/testdata/check_all.ts b/cli/tests/testdata/check_all.ts new file mode 100644 index 0000000000..2ae8c2692c --- /dev/null +++ b/cli/tests/testdata/check_all.ts @@ -0,0 +1,3 @@ +import * as a from "http://localhost:4545/subdir/type_error.ts"; + +console.log(a.a); diff --git a/cli/tests/testdata/future_check.ts b/cli/tests/testdata/future_check.ts new file mode 100644 index 0000000000..4d41fe06a8 --- /dev/null +++ b/cli/tests/testdata/future_check.ts @@ -0,0 +1 @@ +Deno.metrics(); diff --git a/cli/tests/testdata/future_check1.out b/cli/tests/testdata/future_check1.out new file mode 100644 index 0000000000..9c7592fc55 --- /dev/null +++ b/cli/tests/testdata/future_check1.out @@ -0,0 +1,3 @@ +Warning In future releases `deno run` will not automatically type check without the --check flag. +To opt into this new behavior now, specify DENO_FUTURE_CHECK=1. +Check [WILDCARD]/future_check.ts diff --git a/cli/tests/testdata/future_check2.out b/cli/tests/testdata/future_check2.out new file mode 100644 index 0000000000..c626a5485c --- /dev/null +++ b/cli/tests/testdata/future_check2.out @@ -0,0 +1 @@ +Check [WILDCARD]/future_check.ts diff --git a/cli/tools/bench.rs b/cli/tools/bench.rs index d852139e3f..2d35c27c56 100644 --- a/cli/tools/bench.rs +++ b/cli/tools/bench.rs @@ -11,7 +11,7 @@ use crate::file_watcher; use crate::file_watcher::ResolutionResult; use crate::flags::BenchFlags; use crate::flags::Flags; -use crate::flags::TypecheckMode; +use crate::flags::TypeCheckMode; use crate::fs_util::collect_specifiers; use crate::fs_util::is_supported_bench_path; use crate::graph_util::contains_specifier; @@ -517,7 +517,7 @@ pub async fn run_benchmarks_with_watch( let include = bench_flags.include.unwrap_or_else(|| vec![".".to_string()]); let ignore = bench_flags.ignore.clone(); let paths_to_watch: Vec<_> = include.iter().map(PathBuf::from).collect(); - let no_check = ps.flags.typecheck_mode == TypecheckMode::None; + let no_check = ps.flags.type_check_mode == TypeCheckMode::None; let resolver = |changed: Option>| { let mut cache = cache::FetchCacher::new( diff --git a/cli/tools/installer.rs b/cli/tools/installer.rs index a4340e98c2..8ebbf8f539 100644 --- a/cli/tools/installer.rs +++ b/cli/tools/installer.rs @@ -2,7 +2,7 @@ use crate::flags::Flags; use crate::flags::InstallFlags; -use crate::flags::TypecheckMode; +use crate::flags::TypeCheckMode; use crate::fs_util::canonicalize_path; use deno_core::error::generic_error; use deno_core::error::AnyError; @@ -306,10 +306,10 @@ fn resolve_shim_data( // we should avoid a default branch here to ensure we continue to cover any // changes to this flag. - match flags.typecheck_mode { - TypecheckMode::All => (), - TypecheckMode::None => executable_args.push("--no-check".to_string()), - TypecheckMode::Local => { + match flags.type_check_mode { + TypeCheckMode::All => (), + TypeCheckMode::None => executable_args.push("--no-check".to_string()), + TypeCheckMode::Local => { executable_args.push("--no-check=remote".to_string()) } } @@ -590,7 +590,7 @@ mod tests { &Flags { allow_net: Some(vec![]), allow_read: Some(vec![]), - typecheck_mode: TypecheckMode::None, + type_check_mode: TypeCheckMode::None, log_level: Some(Level::Error), compat: true, ..Flags::default() diff --git a/cli/tools/standalone.rs b/cli/tools/standalone.rs index e7c279f420..9f24b5f088 100644 --- a/cli/tools/standalone.rs +++ b/cli/tools/standalone.rs @@ -4,8 +4,9 @@ use crate::deno_dir::DenoDir; use crate::flags::CompileFlags; use crate::flags::DenoSubcommand; use crate::flags::Flags; +use crate::flags::FutureTypeCheckMode; use crate::flags::RunFlags; -use crate::flags::TypecheckMode; +use crate::flags::TypeCheckMode; use crate::fs_util; use crate::standalone::Metadata; use crate::standalone::MAGIC_TRAILER; @@ -274,7 +275,9 @@ pub fn compile_to_runtime_flags( lock_write: false, lock: None, log_level: flags.log_level, - typecheck_mode: TypecheckMode::All, + type_check_mode: TypeCheckMode::All, + future_type_check_mode: FutureTypeCheckMode::None, + has_check_flag: false, compat: flags.compat, unsafely_ignore_certificate_errors: flags .unsafely_ignore_certificate_errors diff --git a/cli/tools/test.rs b/cli/tools/test.rs index 242abab1b0..96ee3ab6e9 100644 --- a/cli/tools/test.rs +++ b/cli/tools/test.rs @@ -12,7 +12,7 @@ use crate::file_watcher; use crate::file_watcher::ResolutionResult; use crate::flags::Flags; use crate::flags::TestFlags; -use crate::flags::TypecheckMode; +use crate::flags::TypeCheckMode; use crate::fs_util::collect_specifiers; use crate::fs_util::is_supported_test_ext; use crate::fs_util::is_supported_test_path; @@ -1075,7 +1075,7 @@ pub async fn run_tests_with_watch( let include = test_flags.include.unwrap_or_else(|| vec![".".to_string()]); let ignore = test_flags.ignore.clone(); let paths_to_watch: Vec<_> = include.iter().map(PathBuf::from).collect(); - let no_check = ps.flags.typecheck_mode == TypecheckMode::None; + let no_check = ps.flags.type_check_mode == TypeCheckMode::None; let resolver = |changed: Option>| { let mut cache = cache::FetchCacher::new(