summaryrefslogtreecommitdiff
path: root/cli
diff options
context:
space:
mode:
authorKayla Washburn <mckayla@hey.com>2022-06-08 15:30:16 -0600
committerGitHub <noreply@github.com>2022-06-08 15:30:16 -0600
commit94068b7109af64eba2cb9fd299e62705a5358069 (patch)
tree7ba43427fb32d43009437898bbd336932c02e754 /cli
parenta0a13b3a1b5b654ad36a25c4785cab539555840a (diff)
feat(task): add `--cwd` flag for configuring the working directory (#14823)
Diffstat (limited to 'cli')
-rw-r--r--cli/flags.rs63
-rw-r--r--cli/tests/integration/task_tests.rs7
-rw-r--r--cli/tests/testdata/task/deno.json3
-rw-r--r--cli/tests/testdata/task/task_cwd.out1
-rw-r--r--cli/tests/testdata/task/task_no_args.out2
-rw-r--r--cli/tests/testdata/task/task_non_existent.out2
-rw-r--r--cli/tools/task.rs9
7 files changed, 81 insertions, 6 deletions
diff --git a/cli/flags.rs b/cli/flags.rs
index dbb716df8..f4f162dcd 100644
--- a/cli/flags.rs
+++ b/cli/flags.rs
@@ -163,6 +163,7 @@ pub struct RunFlags {
#[derive(Clone, Debug, PartialEq, Deserialize, Serialize)]
pub struct TaskFlags {
+ pub cwd: Option<String>,
pub task: String,
}
@@ -1465,6 +1466,14 @@ fn task_subcommand<'a>() -> Command<'a> {
Command::new("task")
.trailing_var_arg(true)
.args(config_args())
+ .arg(
+ Arg::new("cwd")
+ .long("cwd")
+ .value_name("DIR")
+ .help("Specify the directory to run the task in")
+ .takes_value(true)
+ .value_hint(ValueHint::DirPath)
+ )
// Ideally the task name and trailing arguments should be two separate clap
// arguments, but there is a bug in clap that's preventing us from doing
// this (https://github.com/clap-rs/clap/issues/1538). Once that's fixed,
@@ -2567,7 +2576,15 @@ fn task_parse(
) {
config_args_parse(flags, matches);
- let mut task_name = "".to_string();
+ let mut task_flags = TaskFlags {
+ cwd: None,
+ task: String::new(),
+ };
+
+ if let Some(cwd) = matches.value_of("cwd") {
+ task_flags.cwd = Some(cwd.to_string());
+ }
+
if let Some(mut index) = matches.index_of("task_name_and_args") {
index += 1; // skip `task`
@@ -2578,6 +2595,10 @@ fn task_parse(
flags.config_flag = ConfigFlag::Path(raw_args[index + 1].to_string());
index += 2;
}
+ "--cwd" => {
+ task_flags.cwd = Some(raw_args[index + 1].to_string());
+ index += 2;
+ }
"--no-config" => {
flags.config_flag = ConfigFlag::Disabled;
index += 1;
@@ -2591,7 +2612,7 @@ fn task_parse(
}
if index < raw_args.len() {
- task_name = raw_args[index].to_string();
+ task_flags.task = raw_args[index].to_string();
index += 1;
if index < raw_args.len() {
@@ -2602,7 +2623,7 @@ fn task_parse(
}
}
- flags.subcommand = DenoSubcommand::Task(TaskFlags { task: task_name });
+ flags.subcommand = DenoSubcommand::Task(task_flags);
}
fn test_parse(flags: &mut Flags, matches: &clap::ArgMatches) {
@@ -5597,6 +5618,7 @@ mod tests {
r.unwrap(),
Flags {
subcommand: DenoSubcommand::Task(TaskFlags {
+ cwd: None,
task: "build".to_string(),
}),
argv: svec!["hello", "world"],
@@ -5609,6 +5631,19 @@ mod tests {
r.unwrap(),
Flags {
subcommand: DenoSubcommand::Task(TaskFlags {
+ cwd: None,
+ task: "build".to_string(),
+ }),
+ ..Flags::default()
+ }
+ );
+
+ let r = flags_from_vec(svec!["deno", "task", "--cwd", "foo", "build"]);
+ assert_eq!(
+ r.unwrap(),
+ Flags {
+ subcommand: DenoSubcommand::Task(TaskFlags {
+ cwd: Some("foo".to_string()),
task: "build".to_string(),
}),
..Flags::default()
@@ -5632,6 +5667,7 @@ mod tests {
r.unwrap(),
Flags {
subcommand: DenoSubcommand::Task(TaskFlags {
+ cwd: None,
task: "build".to_string(),
}),
argv: svec!["--", "hello", "world"],
@@ -5639,6 +5675,21 @@ mod tests {
..Flags::default()
}
);
+
+ let r = flags_from_vec(svec![
+ "deno", "task", "--cwd", "foo", "build", "--", "hello", "world"
+ ]);
+ assert_eq!(
+ r.unwrap(),
+ Flags {
+ subcommand: DenoSubcommand::Task(TaskFlags {
+ cwd: Some("foo".to_string()),
+ task: "build".to_string(),
+ }),
+ argv: svec!["--", "hello", "world"],
+ ..Flags::default()
+ }
+ );
}
#[test]
@@ -5649,6 +5700,7 @@ mod tests {
r.unwrap(),
Flags {
subcommand: DenoSubcommand::Task(TaskFlags {
+ cwd: None,
task: "build".to_string(),
}),
argv: svec!["--"],
@@ -5664,6 +5716,7 @@ mod tests {
r.unwrap(),
Flags {
subcommand: DenoSubcommand::Task(TaskFlags {
+ cwd: None,
task: "build".to_string(),
}),
argv: svec!["-1", "--test"],
@@ -5679,6 +5732,7 @@ mod tests {
r.unwrap(),
Flags {
subcommand: DenoSubcommand::Task(TaskFlags {
+ cwd: None,
task: "build".to_string(),
}),
argv: svec!["--test"],
@@ -5694,6 +5748,7 @@ mod tests {
r.unwrap(),
Flags {
subcommand: DenoSubcommand::Task(TaskFlags {
+ cwd: None,
task: "".to_string(),
}),
..Flags::default()
@@ -5708,6 +5763,7 @@ mod tests {
r.unwrap(),
Flags {
subcommand: DenoSubcommand::Task(TaskFlags {
+ cwd: None,
task: "".to_string(),
}),
config_flag: ConfigFlag::Path("deno.jsonc".to_string()),
@@ -5723,6 +5779,7 @@ mod tests {
r.unwrap(),
Flags {
subcommand: DenoSubcommand::Task(TaskFlags {
+ cwd: None,
task: "".to_string(),
}),
config_flag: ConfigFlag::Path("deno.jsonc".to_string()),
diff --git a/cli/tests/integration/task_tests.rs b/cli/tests/integration/task_tests.rs
index e2adc85d9..837d9d2b7 100644
--- a/cli/tests/integration/task_tests.rs
+++ b/cli/tests/integration/task_tests.rs
@@ -12,6 +12,13 @@ itest!(task_no_args {
exit_code: 1,
});
+itest!(task_cwd {
+ args: "task -q --config task/deno.json --cwd .. echo_cwd",
+ output: "task/task_cwd.out",
+ envs: vec![("NO_COLOR".to_string(), "1".to_string())],
+ exit_code: 0,
+});
+
itest!(task_non_existent {
args: "task --config task/deno.json non_existent",
output: "task/task_non_existent.out",
diff --git a/cli/tests/testdata/task/deno.json b/cli/tests/testdata/task/deno.json
index 279c7ea8b..229315a4e 100644
--- a/cli/tests/testdata/task/deno.json
+++ b/cli/tests/testdata/task/deno.json
@@ -5,6 +5,7 @@
"deno_echo": "deno eval 'console.log(5)'",
"strings": "deno run main.ts && deno eval \"console.log(\\\"test\\\")\"",
"piped": "echo 12345 | (deno eval 'const b = new Uint8Array(1);Deno.stdin.readSync(b);console.log(b)' && deno eval 'const b = new Uint8Array(1);Deno.stdin.readSync(b);console.log(b)')",
- "exit_code_5": "echo $(echo 10 ; exit 2) && exit 5"
+ "exit_code_5": "echo $(echo 10 ; exit 2) && exit 5",
+ "echo_cwd": "echo $(pwd)"
}
}
diff --git a/cli/tests/testdata/task/task_cwd.out b/cli/tests/testdata/task/task_cwd.out
new file mode 100644
index 000000000..bfe3e7b11
--- /dev/null
+++ b/cli/tests/testdata/task/task_cwd.out
@@ -0,0 +1 @@
+[WILDCARD]tests
diff --git a/cli/tests/testdata/task/task_no_args.out b/cli/tests/testdata/task/task_no_args.out
index e8c034a2d..d7e509656 100644
--- a/cli/tests/testdata/task/task_no_args.out
+++ b/cli/tests/testdata/task/task_no_args.out
@@ -5,6 +5,8 @@ Available tasks:
deno eval 'console.log(5)'
- echo
echo 1
+- echo_cwd
+ echo $(pwd)
- exit_code_5
echo $(echo 10 ; exit 2) && exit 5
- piped
diff --git a/cli/tests/testdata/task/task_non_existent.out b/cli/tests/testdata/task/task_non_existent.out
index bd4b73c6f..4867d3068 100644
--- a/cli/tests/testdata/task/task_non_existent.out
+++ b/cli/tests/testdata/task/task_non_existent.out
@@ -7,6 +7,8 @@ Available tasks:
deno eval 'console.log(5)'
- echo
echo 1
+- echo_cwd
+ echo $(pwd)
- exit_code_5
echo $(echo 10 ; exit 2) && exit 5
- piped
diff --git a/cli/tools/task.rs b/cli/tools/task.rs
index 578fd1100..28dd0a853 100644
--- a/cli/tools/task.rs
+++ b/cli/tools/task.rs
@@ -4,12 +4,14 @@ use crate::colors;
use crate::config_file::ConfigFile;
use crate::flags::Flags;
use crate::flags::TaskFlags;
+use crate::fs_util;
use crate::proc_state::ProcState;
use deno_core::anyhow::bail;
use deno_core::anyhow::Context;
use deno_core::error::AnyError;
use std::collections::BTreeMap;
use std::collections::HashMap;
+use std::path::PathBuf;
use std::sync::Arc;
fn get_tasks_config(
@@ -71,7 +73,10 @@ pub async fn execute_script(
return Ok(1);
}
- let cwd = config_file_path.parent().unwrap();
+ let cwd = match task_flags.cwd {
+ Some(path) => fs_util::canonicalize_path(&PathBuf::from(path))?,
+ None => config_file_path.parent().unwrap().to_owned(),
+ };
let task_name = task_flags.task;
let maybe_script = tasks_config.get(&task_name);
@@ -95,7 +100,7 @@ pub async fn execute_script(
let seq_list = deno_task_shell::parser::parse(script)
.with_context(|| format!("Error parsing script '{}'.", task_name))?;
let env_vars = std::env::vars().collect::<HashMap<String, String>>();
- let exit_code = deno_task_shell::execute(seq_list, env_vars, cwd).await;
+ let exit_code = deno_task_shell::execute(seq_list, env_vars, &cwd).await;
Ok(exit_code)
} else {
eprintln!("Task not found: {}", task_name);