如何执行参数中带引号的命令?
How do I execute a command with quotation marks in an argument?
我正在尝试 运行 命令
rsync -rtv -e 'ssh -i /Users/yuanlinfeng/.ssh/id_rsa -o "UserKnownHostsFile=/dev/null" -o "StrictHostKeyChecking no" -o "ConnectTimeout=2"' /tmp/a username@ip:/home/ubuntu/a
密码是:
let login_settings = format!(r#"'ssh -i {} -o "UserKnownHostsFile=/dev/null" -o "StrictHostKeyChecking no" -o "ConnectTimeout=2"'"#, identity);
let mut cmd = Command::new("rsync");
cmd.env("SETTING", login_settings);
cmd.arg("-rtv").arg("-e").arg(login_settings);
if delete {
cmd.arg("--delete");
}
match exclude_files {
None => {}
Some(exclude_files) => {
for file in exclude_files.iter() {
cmd.arg("--exclude").arg(file);
}
}
}
let target = format!("{}@{}:{}", username, remote_ip, dest);
cmd.arg(source).arg(target);
let output = cmd.output()?;
if output.stdout.len() > 0 {
println!("stdout: {}", String::from_utf8_lossy(&output.stdout));
}
if output.stderr.len() > 0 {
println!("stderr: {}", String::from_utf8_lossy(&output.stderr));
}
错误:
stderr: rsync: Failed to exec ssh -i /Users/yuanlinfeng/.ssh/id_rsa -o "UserKnownHostsFile=/dev/null" -o "StrictHostKeyChecking no" -o "ConnectTimeout=2": No such file or directory (2)
rsync error: error in IPC code (code 14) at /BuildRoot/Library/Caches/com.apple.xbs/Sources/rsync/rsync-52/rsync/pipe.c(86) [sender=2.6.9]
rsync: connection unexpectedly closed (0 bytes received so far) [sender]
rsync error: error in rsync protocol data stream (code 12) at /BuildRoot/Library/Caches/com.apple.xbs/Sources/rsync/rsync-52/rsync/io.c(453) [sender=2.6.9]
看起来参数中的引号已被删除。我该如何解决?
我正在使用 macOS High Sierra 和 Rust 1.22.1。
ssh ...
参数周围的 '
引号实际上并未传递给 rsync
; shell 使用它们来分隔 rsync
.
的参数
您的 Rust 代码尝试调用如下内容:rsync -e "'ssh ...'" ...
。然后 rsync 尝试拆分类似于 shell 的 'ssh ...'
参数(似乎它实际上并没有使用 shell 来扩展它)。这意味着它会将 ssh ...
视为一个参数(要执行的文件名),但这样的文件不存在。
删除 format!
调用中的 '
引号,它可能会起作用。
在 Linux 上,您可以通过 strace -ff -e trace=execve -- ./target/...
运行 您的示例来了解它是如何工作的。 macOS 有 dtruss
,但我帮不了你 :)
我正在尝试 运行 命令
rsync -rtv -e 'ssh -i /Users/yuanlinfeng/.ssh/id_rsa -o "UserKnownHostsFile=/dev/null" -o "StrictHostKeyChecking no" -o "ConnectTimeout=2"' /tmp/a username@ip:/home/ubuntu/a
密码是:
let login_settings = format!(r#"'ssh -i {} -o "UserKnownHostsFile=/dev/null" -o "StrictHostKeyChecking no" -o "ConnectTimeout=2"'"#, identity);
let mut cmd = Command::new("rsync");
cmd.env("SETTING", login_settings);
cmd.arg("-rtv").arg("-e").arg(login_settings);
if delete {
cmd.arg("--delete");
}
match exclude_files {
None => {}
Some(exclude_files) => {
for file in exclude_files.iter() {
cmd.arg("--exclude").arg(file);
}
}
}
let target = format!("{}@{}:{}", username, remote_ip, dest);
cmd.arg(source).arg(target);
let output = cmd.output()?;
if output.stdout.len() > 0 {
println!("stdout: {}", String::from_utf8_lossy(&output.stdout));
}
if output.stderr.len() > 0 {
println!("stderr: {}", String::from_utf8_lossy(&output.stderr));
}
错误:
stderr: rsync: Failed to exec ssh -i /Users/yuanlinfeng/.ssh/id_rsa -o "UserKnownHostsFile=/dev/null" -o "StrictHostKeyChecking no" -o "ConnectTimeout=2": No such file or directory (2)
rsync error: error in IPC code (code 14) at /BuildRoot/Library/Caches/com.apple.xbs/Sources/rsync/rsync-52/rsync/pipe.c(86) [sender=2.6.9]
rsync: connection unexpectedly closed (0 bytes received so far) [sender]
rsync error: error in rsync protocol data stream (code 12) at /BuildRoot/Library/Caches/com.apple.xbs/Sources/rsync/rsync-52/rsync/io.c(453) [sender=2.6.9]
看起来参数中的引号已被删除。我该如何解决?
我正在使用 macOS High Sierra 和 Rust 1.22.1。
ssh ...
参数周围的 '
引号实际上并未传递给 rsync
; shell 使用它们来分隔 rsync
.
您的 Rust 代码尝试调用如下内容:rsync -e "'ssh ...'" ...
。然后 rsync 尝试拆分类似于 shell 的 'ssh ...'
参数(似乎它实际上并没有使用 shell 来扩展它)。这意味着它会将 ssh ...
视为一个参数(要执行的文件名),但这样的文件不存在。
删除 format!
调用中的 '
引号,它可能会起作用。
在 Linux 上,您可以通过 strace -ff -e trace=execve -- ./target/...
运行 您的示例来了解它是如何工作的。 macOS 有 dtruss
,但我帮不了你 :)