我需要按如下方式执行 shell 命令:
ssh <device> "command"
命令的调用方式为:
$(typeset); <function_name> "arguement_string"; cd ...; ls ...
这里到底如何引用?这是对的吗?
""$(typeset); <function_name> "arguement_string""; cd ...; ls ..."
我对 shell 脚本中的这种引用感到困惑。
不要试图手动引用 - 让外壳为您完成!
command_array=( function_name "first argument" "second argument" )
printf -v command_str '%q ' "${command_array[@]}"
ssh_str="$(typeset); $command_str"
ssh machine "$ssh_str"
然后,您可以根据需要构建command_array
- 使用逻辑有条件地附加值,仅使用您通常引用的引用来使用这些值,并让printf %q
添加使内容安全通过ssh所需的所有其他引用。
如果您尝试以增量方式构建脚本,则可以这样做:
remote_script="$(typeset)"$'n'
safe_append_command() {
local command_str
printf -v command_str '%q ' "$@"
remote_script+="$command_str"$'n'
}
safe_append_command cp "$file" "$destination"
safe_append_command tar -cf /tmp/foo.tar "${destination%/*}"
# ...etc...
ssh machine "$remote_script"
请注意,在这种情况下,所有扩展都在本地进行,当生成脚本时,并且不能使用诸如重定向运算符之类的 shell 构造(除非将它们嵌入到函数中,然后使用 typeset
传递给远程系统)。这样做意味着传递给safe_append_command
的任何数据都不能被视为代码 - 以牺牲灵活性为代价排除大量潜在的安全漏洞。
我会在这里使用一个文档:
ssh machine <<'EOF'
hello() {
echo "hello $1!"
}
hello "world"
EOF
请注意,我将起始EOF
括在单引号中。这样做可以防止 bash 解释本地 shell 中的变量或命令替换。