Repository: denoland/deno
Pull request: feat: treat bare deno command with run arguments as deno run 

removes the necessity for the `run` subcommand to run scripts

fixes #24493 

Changed files:
filename: cli/args/flags.rs
patch: @@ -1207,7 +1207,7 @@ pub fn flags_from_vec(args: Vec<OsString>) -> clap::error::Result<Flags> {
       "lint" => lint_parse(&mut flags, &mut m),
       "lsp" => lsp_parse(&mut flags, &mut m),
       "repl" => repl_parse(&mut flags, &mut m),
-      "run" => run_parse(&mut flags, &mut m, app)?,
+      "run" => run_parse(&mut flags, &mut m, app, true)?,
       "serve" => serve_parse(&mut flags, &mut m, app)?,
       "task" => task_parse(&mut flags, &mut m),
       "test" => test_parse(&mut flags, &mut m),
@@ -1219,14 +1219,27 @@ pub fn flags_from_vec(args: Vec<OsString>) -> clap::error::Result<Flags> {
       _ => unreachable!(),
     }
   } else {
-    handle_repl_flags(
-      &mut flags,
-      ReplFlags {
-        eval_files: None,
-        eval: None,
-        is_default_command: true,
-      },
-    )
+    let has_non_globals = app
+      .get_arguments()
+      .filter(|arg| !arg.is_global_set())
+      .any(|arg| {
+        matches
+          .value_source(arg.get_id().as_str())
+          .is_some_and(|value| value != clap::parser::ValueSource::DefaultValue)
+      });
+
+    if has_non_globals || matches.contains_id("script_arg") {
+      run_parse(&mut flags, &mut matches, app, false)?;
+    } else {
+      handle_repl_flags(
+        &mut flags,
+        ReplFlags {
+          eval_files: None,
+          eval: None,
+          is_default_command: true,
+        },
+      )
+    }
   }
 
   Ok(flags)
@@ -1261,7 +1274,7 @@ fn clap_root() -> Command {
     crate::version::TYPESCRIPT
   );
 
-  let mut cmd = Command::new("deno")
+  let mut cmd = run_args(Command::new("deno"), true)
     .bin_name("deno")
     .styles(
       clap::builder::Styles::styled()
@@ -1432,7 +1445,7 @@ glob {*_,*.,}bench.{js,mjs,ts,mts,jsx,tsx}:
   deno bench src/",
     )
     .defer(|cmd| {
-      runtime_args(cmd, true, false)
+      runtime_args(cmd, true, false, false)
         .arg(check_arg(true))
         .arg(
           Arg::new("json")
@@ -1492,7 +1505,7 @@ If no output file is given, the output is written to standard output:
   deno bundle jsr:@std/http/file-server",
     )
     .defer(|cmd| {
-      compile_args(cmd)
+      compile_args(cmd, false)
         .hide(true)
         .arg(check_arg(true))
         .arg(
@@ -1523,7 +1536,7 @@ Future runs of this module will trigger no downloads or compilation unless
 --reload is specified.",
     )
     .defer(|cmd| {
-      compile_args(cmd)
+      compile_args(cmd, false)
         .arg(check_arg(false))
         .arg(
           Arg::new("file")
@@ -1550,7 +1563,7 @@ fn check_subcommand() -> Command {
 
 Unless --reload is specified, this command will not re-download already cached dependencies.",
       )
-    .defer(|cmd| compile_args_without_check_args(cmd).arg(
+    .defer(|cmd| compile_args_without_check_args(cmd, false).arg(
       Arg::new("all")
         .long("all")
         .help("Type-check all code, including remote modules and npm packages")
@@ -1601,7 +1614,7 @@ supported in canary.
 ",
     )
     .defer(|cmd| {
-      runtime_args(cmd, true, false)
+      runtime_args(cmd, true, false, false)
       .arg(check_arg(true))
       .arg(
         Arg::new("include")
@@ -1933,7 +1946,7 @@ To evaluate as TypeScript:
 This command has implicit access to all permissions (--allow-all).",
     )
     .defer(|cmd| {
-      runtime_args(cmd, false, true)
+      runtime_args(cmd, false, true, false)
         .arg(check_arg(false))
         .arg(
           // TODO(@satyarohith): remove this argument in 2.0.
@@ -2256,7 +2269,7 @@ The installation root is determined, in order of precedence:
 
 These must be added to the path manually if required.")
     .defer(|cmd| {
-      let cmd = runtime_args(cmd, true, true).arg(check_arg(true)).arg(allow_scripts_arg());
+      let cmd = runtime_args(cmd, true, true, false).arg(check_arg(true)).arg(allow_scripts_arg());
       install_args(cmd, true)
     })
 }
@@ -2293,7 +2306,7 @@ The installation root is determined, in order of precedence:
 
 These must be added to the path manually if required.")
     .defer(|cmd| {
-      let cmd = runtime_args(cmd, true, true).arg(check_arg(true));
+      let cmd = runtime_args(cmd, true, true, false).arg(check_arg(true));
       install_args(cmd, false)
     })
 }
@@ -2492,7 +2505,7 @@ Ignore linting a file by adding an ignore comment at the top of the file:
 fn repl_subcommand() -> Command {
   Command::new("repl")
     .about("Read Eval Print Loop")
-    .defer(|cmd| runtime_args(cmd, true, true)
+    .defer(|cmd| runtime_args(cmd, true, true, false)
       .arg(check_arg(false))
       .arg(
         Arg::new("eval-file")
@@ -2512,21 +2525,27 @@ fn repl_subcommand() -> Command {
       .arg(env_file_arg())
 }
 
-fn run_subcommand() -> Command {
-  runtime_args(Command::new("run"), true, true)
-    .arg(check_arg(false))
-    .arg(watch_arg(true))
-    .arg(watch_exclude_arg())
-    .arg(hmr_arg(true))
-    .arg(no_clear_screen_arg())
-    .arg(executable_ext_arg())
-    .arg(
+fn run_args(command: Command, top_level: bool) -> Command {
+  runtime_args(command, true, true, top_level)
+    .arg(check_arg(false).hide(top_level))
+    .arg(watch_arg(true).hide(top_level))
+    .arg(watch_exclude_arg().hide(top_level))
+    .arg(hmr_arg(true).hide(top_level))
+    .arg(no_clear_screen_arg().hide(top_level))
+    .arg(executable_ext_arg().hide(top_level))
+    .arg(if top_level {
+      script_arg().trailing_var_arg(true).hide(true)
+    } else {
       script_arg()
         .required_unless_present("v8-flags")
-        .trailing_var_arg(true),
-    )
-    .arg(env_file_arg())
-    .arg(no_code_cache_arg())
+        .trailing_var_arg(true)
+    })
+    .arg(env_file_arg().hide(top_level))
+    .arg(no_code_cache_arg().hide(top_level))
+}
+
+fn run_subcommand() -> Command {
+  run_args(Command::new("run"), false)
     .about("Run a JavaScript or TypeScript program")
     .long_about(
       "Run a JavaScript or TypeScript program
@@ -2563,7 +2582,7 @@ fn serve_host_validator(host: &str) -> Result<String, String> {
 }
 
 fn serve_subcommand() -> Command {
-  runtime_args(Command::new("serve"), true, true)
+  runtime_args(Command::new("serve"), true, true, false)
     .arg(
       Arg::new("port")
         .long("port")
@@ -2646,7 +2665,7 @@ Directory arguments are expanded to all contained files matching the glob
 
   deno test src/",
     )
-  .defer(|cmd| runtime_args(cmd, true, true)
+  .defer(|cmd| runtime_args(cmd, true, true, false)
     .arg(check_arg(true))
     .arg(
       Arg::new("ignore")
@@ -2951,24 +2970,24 @@ fn publish_subcommand() -> Command {
     })
 }
 
-fn compile_args(app: Command) -> Command {
-  compile_args_without_check_args(app.arg(no_check_arg()))
+fn compile_args(app: Command, hide: bool) -> Command {
+  compile_args_without_check_args(app.arg(no_check_arg().hide(hide)), hide)
 }
 
-fn compile_args_without_check_args(app: Command) -> Command {
+fn compile_args_without_check_args(app: Command, hide: bool) -> Command {
   app
-    .arg(import_map_arg())
-    .arg(no_remote_arg())
-    .arg(no_npm_arg())
-    .arg(node_modules_dir_arg())
-    .arg(vendor_arg())
-    .arg(config_arg())
-    .arg(no_config_arg())
-    .arg(reload_arg())
-    .arg(lock_arg())
+    .arg(import_map_arg().hide(hide))
+    .arg(no_remote_arg().hide(hide))
+    .arg(no_npm_arg().hide(hide))
+    .arg(node_modules_dir_arg().hide(hide))
+    .arg(vendor_arg().hide(hide))
+    .arg(config_arg().hide(hide))
+    .arg(no_config_arg().hide(hide))
+    .arg(reload_arg().hide(hide))
+    .arg(lock_arg().hide(hide))
     .arg(lock_write_arg())
-    .arg(no_lock_arg())
-    .arg(ca_file_arg())
+    .arg(no_lock_arg().hide(hide))
+    .arg(ca_file_arg().hide(hide))
 }
 
 static ALLOW_READ_HELP: &str = concat!(
@@ -3132,7 +3151,7 @@ static ALLOW_ALL_HELP: &str = concat!(
   "/basics/permissions\n"
 );
 
-fn permission_args(app: Command) -> Command {
+fn permission_args(app: Command, hide: bool) -> Command {
   app
     .arg(
       Arg::new("allow-read")
@@ -3144,7 +3163,8 @@ fn permission_args(app: Command) -> Command {
         .value_name("PATH")
         .help(ALLOW_READ_HELP)
         .value_parser(value_parser!(String))
-        .value_hint(ValueHint::AnyPath),
+        .value_hint(ValueHint::AnyPath)
+        .hide(hide),
     )
     .arg(
       Arg::new("deny-read")
@@ -3155,7 +3175,8 @@ fn permission_args(app: Command) -> Command {
         .value_name("PATH")
         .help(DENY_READ_HELP)
         .value_parser(value_parser!(String))
-        .value_hint(ValueHint::AnyPath),
+        .value_hint(ValueHint::AnyPath)
+        .hide(hide),
     )
     .arg(
       Arg::new("allow-write")
@@ -3167,7 +3188,8 @@ fn permission_args(app: Command) -> Command {
         .value_name("PATH")
         .help(ALLOW_WRITE_HELP)
         .value_parser(value_parser!(String))
-        .value_hint(ValueHint::AnyPath),
+        .value_hint(ValueHint::AnyPath)
+        .hide(hide),
     )
     .arg(
       Arg::new("deny-write")
@@ -3178,7 +3200,8 @@ fn permission_args(app: Command) -> Command {
         .value_name("PATH")
         .help(DENY_WRITE_HELP)
         .value_parser(value_parser!(String))
-        .value_hint(ValueHint::AnyPath),
+        .value_hint(ValueHint::AnyPath)
+        .hide(hide),
     )
     .arg(
       Arg::new("allow-net")
@@ -3189,7 +3212,8 @@ fn permission_args(app: Command) -> Command {
         .require_equals(true)
         .value_name("IP_OR_HOSTNAME")
         .help(ALLOW_NET_HELP)
-        .value_parser(flags_net::validator),
+        .value_parser(flags_net::validator)
+        .hide(hide),
     )
     .arg(
       Arg::new("deny-net")
@@ -3199,9 +3223,10 @@ fn permission_args(app: Command) -> Command {
         .require_equals(true)
         .value_name("IP_OR_HOSTNAME")
         .help(DENY_NET_HELP)
-        .value_parser(flags_net::validator),
+        .value_parser(flags_net::validator)
+        .hide(hide),
     )
-    .arg(unsafely_ignore_certificate_errors_arg())
+    .arg(unsafely_ignore_certificate_errors_arg().hide(hide))
     .arg(
       Arg::new("allow-env")
         .long("allow-env")
@@ -3221,7 +3246,8 @@ fn permission_args(app: Command) -> Command {
           } else {
             key.to_string()
           })
-        }),
+        })
+        .hide(hide),
     )
     .arg(
       Arg::new("deny-env")
@@ -3241,7 +3267,8 @@ fn permission_args(app: Command) -> Command {
           } else {
             key.to_string()
           })
-        }),
+        })
+        .hide(hide),
     )
     .arg(
       Arg::new("allow-sys")
@@ -3252,7 +3279,8 @@ fn permission_args(app: Command) -> Command {
         .require_equals(true)
         .value_name("API_NAME")
         .help(ALLOW_SYS_HELP)
-        .value_parser(|key: &str| parse_sys_kind(key).map(ToString::to_string)),
+        .value_parser(|key: &str| parse_sys_kind(key).map(ToString::to_string))
+        .hide(hide),
     )
     .arg(
       Arg::new("deny-sys")
@@ -3262,7 +3290,8 @@ fn permission_args(app: Command) -> Command {
         .require_equals(true)
         .value_name("API_NAME")
         .help(DENY_SYS_HELP)
-        .value_parser(|key: &str| parse_sys_kind(key).map(ToString::to_string)),
+        .value_parser(|key: &str| parse_sys_kind(key).map(ToString::to_string))
+        .hide(hide),
     )
     .arg(
       Arg::new("allow-run")
@@ -3271,7 +3300,8 @@ fn permission_args(app: Command) -> Command {
         .use_value_delimiter(true)
         .require_equals(true)
         .value_name("PROGRAM_NAME")
-        .help(ALLOW_RUN_HELP),
+        .help(ALLOW_RUN_HELP)
+        .hide(hide),
     )
     .arg(
       Arg::new("deny-run")
@@ -3280,7 +3310,8 @@ fn permission_args(app: Command) -> Command {
         .use_value_delimiter(true)
         .require_equals(true)
         .value_name("PROGRAM_NAME")
-        .help(DENY_RUN_HELP),
+        .help(DENY_RUN_HELP)
+        .hide(hide),
     )
     .arg(
       Arg::new("allow-ffi")
@@ -3291,7 +3322,8 @@ fn permission_args(app: Command) -> Command {
         .value_name("PATH")
         .help(ALLOW_FFI_HELP)
         .value_parser(value_parser!(String))
-        .value_hint(ValueHint::AnyPath),
+        .value_hint(ValueHint::AnyPath)
+        .hide(hide),
     )
     .arg(
       Arg::new("deny-ffi")
@@ -3302,62 +3334,68 @@ fn permission_args(app: Command) -> Command {
         .value_name("PATH")
         .help(DENY_FFI_HELP)
         .value_parser(value_parser!(String))
-        .value_hint(ValueHint::AnyPath),
+        .value_hint(ValueHint::AnyPath)
+        .hide(hide),
     )
     .arg(
       Arg::new("allow-hrtime")
         .long("allow-hrtime")
         .action(ArgAction::SetTrue)
-        .help(ALLOW_HRTIME_HELP),
+        .help(ALLOW_HRTIME_HELP)
+        .hide(hide),
     )
     .arg(
       Arg::new("deny-hrtime")
         .long("deny-hrtime")
         .action(ArgAction::SetTrue)
-        .help(DENY_HRTIME_HELP),
+        .help(DENY_HRTIME_HELP)
+        .hide(hide),
     )
     .arg(
       Arg::new("allow-all")
         .short('A')
         .long("allow-all")
         .action(ArgAction::SetTrue)
-        .help(ALLOW_ALL_HELP),
+        .help(ALLOW_ALL_HELP)
+        .hide(hide),
     )
     .arg(
       Arg::new("no-prompt")
         .long("no-prompt")
         .action(ArgAction::SetTrue)
-        .help("Always throw if required permission wasn't passed"),
+        .help("Always throw if required permission wasn't passed")
+        .hide(hide),
     )
 }
 
 fn runtime_args(
   app: Command,
   include_perms: bool,
   include_inspector: bool,
+  hide: bool,
 ) -> Command {
-  let app = compile_args(app);
+  let app = compile_args(app, hide);
   let app = if include_perms {
-    permission_args(app)
+    permission_args(app, hide)
   } else {
     app
   };
   let app = if include_inspector {
-    inspect_args(app)
+    inspect_args(app, hide)
   } else {
     app
   };
   app
-    .arg(frozen_lockfile_arg())
-    .arg(cached_only_arg())
-    .arg(location_arg())
-    .arg(v8_flags_arg())
-    .arg(seed_arg())
+    .arg(frozen_lockfile_arg().hide(hide))
+    .arg(cached_only_arg().hide(hide))
+    .arg(location_arg().hide(hide))
+    .arg(v8_flags_arg().hide(hide))
+    .arg(seed_arg().hide(hide))
     .arg(enable_testing_features_arg())
     .arg(strace_ops_arg())
 }
 
-fn inspect_args(app: Command) -> Command {
+fn inspect_args(app: Command, hide: bool) -> Command {
   app
     .arg(
       Arg::new("inspect")
@@ -3366,7 +3404,8 @@ fn inspect_args(app: Command) -> Command {
         .help("Activate inspector on host:port (default: 127.0.0.1:9229)")
         .num_args(0..=1)
         .require_equals(true)
-        .value_parser(value_parser!(SocketAddr)),
+        .value_parser(value_parser!(SocketAddr))
+        .hide(hide),
     )
     .arg(
       Arg::new("inspect-brk")
@@ -3377,7 +3416,8 @@ fn inspect_args(app: Command) -> Command {
         )
         .num_args(0..=1)
         .require_equals(true)
-        .value_parser(value_parser!(SocketAddr)),
+        .value_parser(value_parser!(SocketAddr))
+        .hide(hide),
     )
     .arg(
       Arg::new("inspect-wait")
@@ -3388,7 +3428,8 @@ fn inspect_args(app: Command) -> Command {
         )
         .num_args(0..=1)
         .require_equals(true)
-        .value_parser(value_parser!(SocketAddr)),
+        .value_parser(value_parser!(SocketAddr))
+        .hide(hide),
     )
 }
 
@@ -4281,7 +4322,8 @@ fn repl_parse(flags: &mut Flags, matches: &mut ArgMatches) {
 fn run_parse(
   flags: &mut Flags,
   matches: &mut ArgMatches,
-  app: Command,
+  mut app: Command,
+  is_run_subommand: bool,
 ) -> clap::error::Result<()> {
   // todo(dsherret): remove this in Deno 2.0
   // This is a hack to make https://github.com/netlify/build/pull/5767 work
@@ -4336,12 +4378,17 @@ fn run_parse(
 
   let mut script_arg =
     matches.remove_many::<String>("script_arg").ok_or_else(|| {
-      let mut app = app;
-      let subcommand = &mut app.find_subcommand_mut("run").unwrap();
-      subcommand.error(
-        clap::error::ErrorKind::MissingRequiredArgument,
-        "[SCRIPT_ARG] may only be omitted with --v8-flags=--help",
-      )
+      if is_run_subommand {
+        app.find_subcommand_mut("run").unwrap().error(
+          clap::error::ErrorKind::MissingRequiredArgument,
+          "[SCRIPT_ARG] may only be omitted with --v8-flags=--help",
+        )
+      } else {
+        app.override_usage("deno [OPTIONS] [COMMAND] [SCRIPT_ARG]...").error(
+          clap::error::ErrorKind::MissingRequiredArgument,
+          "[SCRIPT_ARG] may only be omitted with --v8-flags=--help, else to use the repl with arguments, please use the `deno repl` subcommand",
+        )
+      }
     })?;
 
   let script = script_arg.next().unwrap();
@@ -5160,7 +5207,6 @@ mod tests {
 
     let r = flags_from_vec(svec![
       "deno",
-      "run",
       "--watch",
       "--no-clear-screen",
       "script.ts"
@@ -5240,8 +5286,7 @@ mod tests {
 
   #[test]
   fn run_watch_with_external() {
-    let r =
-      flags_from_vec(svec!["deno", "run", "--watch=file1,file2", "script.ts"]);
+    let r = flags_from_vec(svec!["deno", "--watch=file1,file2", "script.ts"]);
     let flags = r.unwrap();
     assert_eq!(
       flags,
@@ -5294,7 +5339,6 @@ mod tests {
   fn run_watch_with_excluded_paths() {
     let r = flags_from_vec(svec!(
       "deno",
-      "run",
       "--watch",
       "--watch-exclude=foo",
       "script.ts"
@@ -5371,7 +5415,6 @@ mod tests {
 
     let r = flags_from_vec(svec![
       "deno",
-      "run",
       "--watch=foo,bar",
       "--watch-exclude=baz,qux",
       "script.ts"
@@ -5607,7 +5650,7 @@ mod tests {
 
   #[test]
   fn has_permission() {
-    let r = flags_from_vec(svec!["deno", "run", "--allow-read", "x.ts"]);
+    let r = flags_from_vec(svec!["deno", "--allow-read", "x.ts"]);
     assert_eq!(r.unwrap().has_permission(), true);
 
     let r = flags_from_vec(svec!["deno", "run", "--deny-read", "x.ts"]);
@@ -5622,7 +5665,7 @@ mod tests {
     let r = flags_from_vec(svec!["deno", "run", "x.ts", "--allow-read"]);
     assert_eq!(r.unwrap().has_permission_in_argv(), true);
 
-    let r = flags_from_vec(svec!["deno", "run", "x.ts", "--deny-read"]);
+    let r = flags_from_vec(svec!["deno", "x.ts", "--deny-read"]);
     assert_eq!(r.unwrap().has_permission_in_argv(), true);
 
     let r = flags_from_vec(svec!["deno", "run", "x.ts"]);
@@ -5724,7 +5767,7 @@ mod tests {
 
   #[test]
   fn deny_read() {
-    let r = flags_from_vec(svec!["deno", "run", "--deny-read", "gist.ts"]);
+    let r = flags_from_vec(svec!["deno", "--deny-read", "gist.ts"]);
     assert_eq!(
       r.unwrap(),
       Flags {
@@ -6972,8 +7015,7 @@ mod tests {
 
   #[test]
   fn deny_net_denylist() {
-    let r =
-      flags_from_vec(svec!["deno", "run", "--deny-net=127.0.0.1", "script.ts"]);
+    let r = flags_from_vec(svec!["deno", "--deny-net=127.0.0.1", "script.ts"]);
     assert_eq!(
       r.unwrap(),
       Flags {
@@ -7079,8 +7121,7 @@ mod tests {
     let r =
       flags_from_vec(svec!["deno", "run", "--allow-env=HOME", "script.ts"]);
     assert!(r.is_ok());
-    let r =
-      flags_from_vec(svec!["deno", "run", "--allow-env=H=ME", "script.ts"]);
+    let r = flags_from_vec(svec!["deno", "--allow-env=H=ME", "script.ts"]);
     assert!(r.is_err());
     let r =
       flags_from_vec(svec!["deno", "run", "--allow-env=H\0ME", "script.ts"]);
@@ -7095,8 +7136,7 @@ mod tests {
     let r =
       flags_from_vec(svec!["deno", "run", "--deny-env=H=ME", "script.ts"]);
     assert!(r.is_err());
-    let r =
-      flags_from_vec(svec!["deno", "run", "--deny-env=H\0ME", "script.ts"]);
+    let r = flags_from_vec(svec!["deno", "--deny-env=H\0ME", "script.ts"]);
     assert!(r.is_err());
   }
 
@@ -7160,8 +7200,7 @@ mod tests {
 
   #[test]
   fn deny_sys_denylist() {
-    let r =
-      flags_from_vec(svec!["deno", "run", "--deny-sys=hostname", "script.ts"]);
+    let r = flags_from_vec(svec!["deno", "--deny-sys=hostname", "script.ts"]);
     assert_eq!(
       r.unwrap(),
       Flags {
@@ -7311,7 +7350,7 @@ mod tests {
       flags_from_vec(svec!["deno", "run", "--reload=/absolute", "script.ts"]);
     assert!(r.is_err(), "Should reject absolute urls");
 
-    let r = flags_from_vec(svec!["deno", "run", "--reload=/", "script.ts"]);
+    let r = flags_from_vec(svec!["deno", "--reload=/", "script.ts"]);
     assert!(r.is_err(), "Should reject absolute root url");
 
     let r = flags_from_vec(svec!["deno", "run", "--reload=", "script.ts"]);
@@ -7640,8 +7679,7 @@ mod tests {
 
   #[test]
   fn run_no_code_cache() {
-    let r =
-      flags_from_vec(svec!["deno", "run", "--no-code-cache", "script.ts"]);
+    let r = flags_from_vec(svec!["deno", "--no-code-cache", "script.ts"]);
     assert_eq!(
       r.unwrap(),
       Flags {
@@ -7891,7 +7929,7 @@ mod tests {
 
   #[test]
   fn quiet() {
-    let r = flags_from_vec(svec!["deno", "run", "-q", "script.ts"]);
+    let r = flags_from_vec(svec!["deno", "-q", "script.ts"]);
     assert_eq!(
       r.unwrap(),
       Flags {
@@ -8009,7 +8047,7 @@ mod tests {
 
   #[test]
   fn no_check() {
-    let r = flags_from_vec(svec!["deno", "run", "--no-check", "script.ts"]);
+    let r = flags_from_vec(svec!["deno", "--no-check", "script.ts"]);
     assert_eq!(
       r.unwrap(),
       Flags {
@@ -8175,8 +8213,7 @@ mod tests {
 
   #[test]
   fn local_npm() {
-    let r =
-      flags_from_vec(svec!["deno", "run", "--node-modules-dir", "script.ts"]);
+    let r = flags_from_vec(svec!["deno", "--node-modules-dir", "script.ts"]);
     assert_eq!(
       r.unwrap(),
       Flags {
@@ -8409,7 +8446,7 @@ mod tests {
       }
     );
 
-    let r = flags_from_vec(svec!["deno", "run", "--no-lock", "script.ts"]);
+    let r = flags_from_vec(svec!["deno", "--no-lock", "script.ts"]);
     assert_eq!(
       r.unwrap(),
       Flags {
@@ -8492,8 +8529,12 @@ mod tests {
 
   #[test]
   fn test_no_colon_in_value_name() {
-    let app =
-      runtime_args(Command::new("test_inspect_completion_value"), true, true);
+    let app = runtime_args(
+      Command::new("test_inspect_completion_value"),
+      true,
+      true,
+      false,
+    );
     let inspect_args = app
       .get_arguments()
       .filter(|arg| arg.get_id() == "inspect")
@@ -9330,7 +9371,7 @@ mod tests {
 
   #[test]
   fn inspect_wait() {
-    let r = flags_from_vec(svec!["deno", "run", "--inspect-wait", "foo.js"]);
+    let r = flags_from_vec(svec!["deno", "--inspect-wait", "foo.js"]);
     assert_eq!(
       r.unwrap(),
       Flags {
@@ -9520,8 +9561,7 @@ mod tests {
     );
 
     let flags =
-      flags_from_vec(svec!["deno", "run", "https://example.com/foo.js"])
-        .unwrap();
+      flags_from_vec(svec!["deno", "https://example.com/foo.js"]).unwrap();
     assert_eq!(flags.config_path_args(&cwd), None);
 
     let flags =
@@ -9929,7 +9969,7 @@ mod tests {
       }
     );
 
-    let r = flags_from_vec(svec!["deno", "run", "--check=foo", "script.ts",]);
+    let r = flags_from_vec(svec!["deno", "--check=foo", "script.ts",]);
     assert_eq!(
       r.unwrap(),
       Flags {
@@ -10232,4 +10272,60 @@ mod tests {
       }
     }
   }
+
+  #[test]
+  fn bare_run() {
+    let r = flags_from_vec(svec!["deno", "--no-config", "script.ts"]);
+    assert_eq!(
+      r.unwrap(),
+      Flags {
+        subcommand: DenoSubcommand::Run(RunFlags::new_default(
+          "script.ts".to_string(),
+        )),
+        config_flag: ConfigFlag::Disabled,
+        code_cache_enabled: true,
+        ..Flags::default()
+      }
+    );
+  }
+
+  #[test]
+  fn bare_global() {
+    let r = flags_from_vec(svec!["deno", "--log-level=debug"]);
+    assert_eq!(
+      r.unwrap(),
+      Flags {
+        subcommand: DenoSubcommand::Repl(ReplFlags {
+          eval_files: None,
+          eval: None,
+          is_default_command: true,
+        }),
+        log_level: Some(Level::Debug),
+        permissions: PermissionFlags {
+          allow_all: false,
+          allow_net: Some(vec![]),
+          allow_env: Some(vec![]),
+          allow_run: Some(vec![]),
+          allow_read: Some(vec![]),
+          allow_sys: Some(vec![]),
+          allow_write: Some(vec![]),
+          allow_ffi: Some(vec![]),
+          allow_hrtime: true,
+          ..Default::default()
+        },
+        ..Flags::default()
+      }
+    );
+  }
+
+  #[test]
+  fn bare_with_flag_no_file() {
+    let r = flags_from_vec(svec!["deno", "--no-config"]);
+
+    let err = r.unwrap_err();
+    assert!(err.to_string().contains("error: [SCRIPT_ARG] may only be omitted with --v8-flags=--help, else to use the repl with arguments, please use the `deno repl` subcommand"));
+    assert!(err
+      .to_string()
+      .contains("Usage: deno [OPTIONS] [COMMAND] [SCRIPT_ARG]..."));
+  }
 }