bash 使用 expect 来生成带有包含空格的参数的命令
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/12518354/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
use expect to spawn command with arguments containing spaces
提问by Richard
I want to use expect
to run a simple command cat /tmp/id_rsa.pub
over ssh.
我想用来通过 sshexpect
运行一个简单的命令cat /tmp/id_rsa.pub
。
In a shell, I can run this wo problem, (with manually put in the password)
在shell中,我可以运行这个wo问题,(手动输入密码)
ssh root@localhost 'cat /tmp/id_rsa.pub'
I want to automate this with expect
. My expect
script is,
我想用expect
. 我的expect
剧本是
#!/usr/bin/expect
eval spawn ssh root@localhost 'cat /tmp/id_rsa.pub'
expect "password:"
send "123456"
expect eof
It throws error bash: cat /tmp/id_rsa.pub: no such file or directory
. it looks very strange to me. What could be the possible cause?
它抛出错误bash: cat /tmp/id_rsa.pub: no such file or directory
。对我来说看起来很奇怪。可能的原因是什么?
Edit: after some testing, I find this is common, not only in the case of cat
. If the argument to spawned command is with space (even if it's in the quotes), it will have problem. For example, replacing cat /tmp/id_rsa.pub
with other commands with spaces, like
编辑:经过一些测试,我发现这很常见,不仅在cat
. 如果 spawned 命令的参数带有空格(即使它在引号中),它也会有问题。例如,用cat /tmp/id_rsa.pub
空格替换其他命令,如
eval spawn ssh root@localhost 'which java'
it complains with bash: which java: command not found
. But if replacing that with pwd
, like
它抱怨bash: which java: command not found
。但是如果用 替换它pwd
,比如
eval spawn ssh root@localhost 'pwd'
it work fine.
它工作正常。
回答by Johannes Kuhn
Single quotes ('
) have no special meaning to Expect, unlike sh and other compatible shells.
This means that your statment
'
与 sh 和其他兼容 shell 不同,单引号 ( ) 对 Expect 没有特殊意义。
这意味着你的声明
spawn ssh root@localhost 'cat /tmp/id_rsa.pub'
is parsed into the following words:
被解析为以下单词:
spawn
ssh
root@localhost
'cat
- not until the other single quote./tmp/id_rsa.pub'
spawn
ssh
root@localhost
'cat
- 直到另一个单引号。/tmp/id_rsa.pub'
The usage in sh is to group this to a single argument. In Tcl you could either use double quotes ("
) or curly brackets ({}
). Inside double quotes, Tcl variables will be substituted, while the content inside {}
is passed without any substitution1.
sh 中的用法是将其分组为单个参数。在 Tcl 中,您可以使用双引号 ( "
) 或大括号 ( {}
)。在双引号内,Tcl 变量将被替换,而里面的内容{}
被传递而没有任何替换1。
tl;drThe Expect/Tcl equivalent of sh's '
are {}
.
tl;dr与 sh 等效的 Expect/Tcl'
是{}
.
1A \
before a newline will still be substitued.
\
换行前的1A仍将被替换。
回答by genesys87
As Johannes said, using '
doesn't work.
I had a similar problem, but I wanted to execute more commands and then still get a login shell. I managed to make it work with "
:
正如约翰内斯所说,使用'
不起作用。
我遇到了类似的问题,但我想执行更多命令,然后仍然获得登录 shell。我设法使它与"
:
expect -c "
set timeout 5;
spawn ssh -XY $user@$host -t \"cat /etc/motd; bash -l\"
expect {
-re \"^Warning.*\" {exp_continue}
-re \"^.*sword: \" {send \"${PASSWORDS[$user]}\r\"; interact}
}
"
回答by mtk
I guess you don't require eval
there. Remove it and check.
我想你不需要eval
那里。取出并检查。
Check this expect examples linkfor detailed examples on "how to use expect
?" .
检查此期望示例链接以获取有关“如何使用expect
?”的详细示例。.
Hope this helps.
希望这可以帮助。