在远程服务器上运行命令单引号混乱! (贝壳)

时间:2013-11-25 21:12:24

标签: shell remote-server

我正在做一个脚本,用户控制在远程服务器上运行的命令

例如

sshpass -p myPassword ssh -q root@127.0.0.1 ''$myCommand''

用户定义$myCommand。但是,如果用户的命令有单引号怎么办!!!它会与我所放的混合在一起。假设用户的命令是

echo 'this is a the remote server `hostname`'

有没有办法解决这个问题?

2 个答案:

答案 0 :(得分:1)

在您给出的示例案例中,似乎并不重要。对于其他类型的报价组合,奇怪的事情确实发生了

$ hostname
laptop1
$ ssh remotehost1 echo 'this is the remote `hostname`'
this is the remote remotehost1
$ ssh remotehost1 echo "this is the remote `hostname`"
this is the remote laptop1
$ ssh remotehost1 echo 'this is the remote \`hostname\`'
this is the remote `hostname`

这是一个更糟糕的例子!

$ ssh remotehost1 ls -l *.txt
ls: cannot access config.txt: No such file or directory
ls: cannot access examples.txt: No such file or directory

在上面的例子中发生的事情是在命令发送到远程之前已经评估了* .txt。它在本地找到名为config.txt和examples.txt的本地文件,但在远程列表中列出它们失败了!

在这种情况下(在大多数情况下)解决方案是用单引号括起整个命令。我相信这是您在系统中做出的决定。

$ ssh remotehost1 'ls -l *.txt'
-rw-r--r-- 1 beaker muppet 15326 2013-03-20 19:08 gs.txt
-rw-r--r-- 1 beaker muppet 30781 2013-05-14 02:07 out.txt
-rw-r--r-- 1 beaker muppet 53567 2013-06-11 18:24 pip-log.txt
-rw-r--r-- 1 beaker muppet  2961 2013-06-28 19:41 plug.txt

如果您希望这样做并在命令中包含单引号,那么它可以在某些时候使用

ssh remotehost1 'ls -l 'gs.txt''
-rw-r--r-- 1 beaker muppet 15326 2013-03-20 19:08 gs.txt

这不起作用的一个案例是

$ ssh remotehost1 'echo 'this is the remote `hostname`''
this is the remote laptop1

这里发生的事情很奇怪。 'echo '被视为一对引号中的字符串。 this is the remote `hostname``` is treated as an unquoted string and finally''`被视为一对引号,其中没有任何内容。因此,在发送ssh命令之前,hostname命令周围的反引号会导致它被评估

要解决这个问题(特别是当命令以root身份运行时),我会拒绝任何带有任何单引号的输入

对于运行更复杂的远程命令,诸如结构http://docs.fabfile.org之类的东西可能更好

答案 1 :(得分:-1)

myCommand=$'echo \'this is the remote server $(hostname)\''
sshpass -p myPassword ssh -q root@127.0.0.1 "$myCommand"

myCommand的值是什么(即使它本身包含双引号)也会传递给远程服务器。

使用''$myCommand'',您只是将空字符串与myCommand扩展产生的第一个和最后一个字连接起来。