diff --git a/crates/nu-cli/src/commands/touch.rs b/crates/nu-cli/src/commands/touch.rs index 0bd7fe549d..19b3e62cb1 100644 --- a/crates/nu-cli/src/commands/touch.rs +++ b/crates/nu-cli/src/commands/touch.rs @@ -10,7 +10,8 @@ pub struct Touch; #[derive(Deserialize)] pub struct TouchArgs { - pub target: Tagged, + target: Tagged, + rest: Vec>, } #[async_trait] @@ -19,14 +20,16 @@ impl WholeStreamCommand for Touch { "touch" } fn signature(&self) -> Signature { - Signature::build("touch").required( - "filename", - SyntaxShape::Path, - "the path of the file you want to create", - ) + Signature::build("touch") + .required( + "filename", + SyntaxShape::Path, + "the path of the file you want to create", + ) + .rest(SyntaxShape::Path, "additional files to create") } fn usage(&self) -> &str { - "creates a file" + "creates one or more files" } async fn run( &self, @@ -37,26 +40,39 @@ impl WholeStreamCommand for Touch { } fn examples(&self) -> Vec { - vec![Example { - description: "Creates \"fixture.json\"", - example: "touch fixture.json", - result: None, - }] + vec![ + Example { + description: "Creates \"fixture.json\"", + example: "touch fixture.json", + result: None, + }, + Example { + description: "Creates files a, b and c", + example: "touch a b c", + result: None, + }, + ] } } async fn touch(args: CommandArgs, registry: &CommandRegistry) -> Result { let registry = registry.clone(); - let (TouchArgs { target }, _) = args.process(®istry).await?; + let (TouchArgs { target, rest }, _) = args.process(®istry).await?; - match OpenOptions::new().write(true).create(true).open(&target) { - Ok(_) => Ok(OutputStream::empty()), - Err(err) => Err(ShellError::labeled_error( - "File Error", - err.to_string(), - &target.tag, - )), + for item in vec![target].into_iter().chain(rest.into_iter()) { + match OpenOptions::new().write(true).create(true).open(&item) { + Ok(_) => continue, + Err(err) => { + return Err(ShellError::labeled_error( + "File Error", + err.to_string(), + &item.tag, + )) + } + } } + + Ok(OutputStream::empty()) } #[cfg(test)] diff --git a/crates/nu-cli/tests/commands/touch.rs b/crates/nu-cli/tests/commands/touch.rs index c527a2143b..affc1d14cc 100644 --- a/crates/nu-cli/tests/commands/touch.rs +++ b/crates/nu-cli/tests/commands/touch.rs @@ -10,7 +10,22 @@ fn creates_a_file_when_it_doesnt_exist() { ); let path = dirs.test().join("i_will_be_created.txt"); - assert!(path.exists()); }) } + +#[test] +fn creates_two_files() { + Playground::setup("create_test_2", |dirs, _sandbox| { + nu!( + cwd: dirs.test(), + "touch a b" + ); + + let path = dirs.test().join("a"); + assert!(path.exists()); + + let path2 = dirs.test().join("b"); + assert!(path2.exists()); + }) +} diff --git a/docs/commands/touch.md b/docs/commands/touch.md index 1dfb8bee89..4c5330febc 100644 --- a/docs/commands/touch.md +++ b/docs/commands/touch.md @@ -1,6 +1,6 @@ # touch -Create a file in the current or an already existent directory. +Create one or more files in the current or an already existent directory. It has no effect on existing files. Unlike GNU touch, the access time and the modified time are not updated. @@ -41,3 +41,15 @@ Create a file within an already existent folder. modified │ 0 secs ago ──────────┴─────────── ``` + +Create three files at oince +```shell +> touch a b c +> ls +────┬────────────────────┬──────┬──────────┬────────────── + # │ name │ type │ size │ modified +────┼────────────────────┼──────┼──────────┼────────────── + 0 │ a │ File │ 0 B │ 0 sec ago + 1 │ b │ File │ 0 B │ 0 sec ago + 2 │ c │ File │ 0 B │ 0 sec ago +────┴────────────────────┴──────┴──────────┴────────────── \ No newline at end of file