Add support for --no-shell option
This commit is contained in:
parent
5d5bc4f17b
commit
ee5e93e6af
|
@ -14,6 +14,7 @@ pub struct Args {
|
|||
pub restart: bool,
|
||||
pub debug: bool,
|
||||
pub run_initially: bool,
|
||||
pub no_shell: bool,
|
||||
pub no_vcs_ignore: bool,
|
||||
pub once: bool,
|
||||
pub poll: bool,
|
||||
|
@ -102,6 +103,10 @@ pub fn get_args() -> Args {
|
|||
.help("Forces polling mode")
|
||||
.long("force-poll")
|
||||
.value_name("interval"))
|
||||
.arg(Arg::with_name("no-shell")
|
||||
.help("Do not wrap command in 'sh -c'")
|
||||
.short("n")
|
||||
.long("no-shell"))
|
||||
.arg(Arg::with_name("once").short("1").hidden(true))
|
||||
.get_matches();
|
||||
|
||||
|
@ -164,6 +169,7 @@ pub fn get_args() -> Args {
|
|||
restart: args.is_present("restart"),
|
||||
debug: args.is_present("debug"),
|
||||
run_initially: !args.is_present("postpone"),
|
||||
no_shell: args.is_present("no-shell"),
|
||||
no_vcs_ignore: args.is_present("no-vcs-ignore"),
|
||||
once: args.is_present("once"),
|
||||
poll: args.occurrences_of("poll") > 0,
|
||||
|
|
|
@ -107,7 +107,7 @@ fn main() {
|
|||
}
|
||||
|
||||
let mut guard = child_process.write().unwrap();
|
||||
*guard = Some(process::spawn(&args.cmd, vec![]));
|
||||
*guard = Some(process::spawn(&args.cmd, vec![], args.no_shell));
|
||||
}
|
||||
|
||||
loop {
|
||||
|
@ -140,7 +140,7 @@ fn main() {
|
|||
debug!("Launching child process");
|
||||
{
|
||||
let mut guard = child_process.write().unwrap();
|
||||
*guard = Some(process::spawn(&args.cmd, paths));
|
||||
*guard = Some(process::spawn(&args.cmd, paths, args.no_shell));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -158,7 +158,7 @@ fn main() {
|
|||
debug!("Launching child process");
|
||||
{
|
||||
let mut guard = child_process.write().unwrap();
|
||||
*guard = Some(process::spawn(&args.cmd, paths));
|
||||
*guard = Some(process::spawn(&args.cmd, paths, args.no_shell));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -179,7 +179,7 @@ fn main() {
|
|||
debug!("Launching child process");
|
||||
{
|
||||
let mut guard = child_process.write().unwrap();
|
||||
*guard = Some(process::spawn(&args.cmd, paths));
|
||||
*guard = Some(process::spawn(&args.cmd, paths, args.no_shell));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
use std::path::PathBuf;
|
||||
|
||||
pub fn spawn(cmd: &str, updated_paths: Vec<PathBuf>) -> Process {
|
||||
self::imp::Process::new(cmd, updated_paths).expect("unable to spawn process")
|
||||
pub fn spawn(cmd: &str, updated_paths: Vec<PathBuf>, no_shell: bool) -> Process {
|
||||
self::imp::Process::new(cmd, updated_paths, no_shell).expect("unable to spawn process")
|
||||
}
|
||||
|
||||
pub use self::imp::Process;
|
||||
|
@ -24,13 +24,33 @@ mod imp {
|
|||
#[allow(unknown_lints)]
|
||||
#[allow(mutex_atomic)]
|
||||
impl Process {
|
||||
pub fn new(cmd: &str, updated_paths: Vec<PathBuf>) -> Result<Process> {
|
||||
pub fn new(cmd: &str, updated_paths: Vec<PathBuf>, no_shell: bool) -> Result<Process> {
|
||||
use nix::unistd::*;
|
||||
use std::io;
|
||||
use std::os::unix::process::CommandExt;
|
||||
|
||||
let mut command = Command::new("sh");
|
||||
command.arg("-c").arg(cmd);
|
||||
// Assemble command to run.
|
||||
// This is either the first argument from cmd (if no_shell was given) or "sh".
|
||||
// Using "sh -c" gives us features like supportin pipes and redirects,
|
||||
// but is a little less performant and can cause trouble when using custom signals
|
||||
// (e.g. --signal SIGHUP)
|
||||
let mut iter_args = cmd.split_whitespace();
|
||||
let arg0 = match no_shell {
|
||||
true => iter_args.next().unwrap(),
|
||||
false => "sh",
|
||||
};
|
||||
|
||||
// TODO: There might be a better way of doing this with &str.
|
||||
// I've had to fall back to String, as I wasn't able to join(" ") a Vec<&str>
|
||||
// into a &str
|
||||
let args: Vec<String> = match no_shell {
|
||||
true => iter_args.map(str::to_string).collect(),
|
||||
false => vec!["-c".to_string(), iter_args.collect::<Vec<&str>>().join(" ")],
|
||||
};
|
||||
|
||||
let mut command = Command::new(arg0);
|
||||
command.args(args);
|
||||
debug!("Assembled command {:?}", command);
|
||||
|
||||
if let Some(single_path) = super::get_single_updated_path(&updated_paths) {
|
||||
command.env("WATCHEXEC_UPDATED_PATH", single_path);
|
||||
|
|
Loading…
Reference in New Issue