如何从shell的'读'命令返回期望脚本中传递?

我对使用期望是一个新的东西,并且对于将命令传递给期望脚本有点困惑,所以请耐心等待…我已经search了很多论坛,但似乎无法find使用read命令的期望脚本的示例获取用户input

在我的Korn shell脚本中,我调用一个expect脚本(expectssh.exp)来sshlogin到另一个主机,并获取有关该主机的networkingconfiguration(networking接口卡号和子网掩码信息)的用户input。 我将四个parameter passing给expect脚本:远程主机ip地址,用户名,密码以及要运行的命令列表。 我期待的脚本如下:

#!/usr/bin/expect # Usage: expectssh <host> <ssh user> <ssh password> <script> set timeout 60 set prompt "(%|#|\\$) $" set commands [lindex $argv 3]; spawn ssh [lindex $argv 1]@[lindex $argv 0] expect { "*assword:" { send -- "[lindex $argv 2]\r" expect -re "$prompt" send -- "$commands\r" } "you sure you want to continue connecting" { send -- "yes\r" expect "*assword:" send -- "[lindex $argv 2]\r" expect -re "$prompt" send -- "$commands\r" } timeout { exit } } 

脚本运行良好,除了当它到达“读取”命令时,脚本不会在用户按下回车键后继续或退出。 它只是挂起。

我传递给expect脚本的命令如下:

 SCRIPT='hostname > response.txt;netstat -rn;read net_card?"What is the network interface card number? " >> response.txt; read net_mask?"What is the subnet mask? " >> response.txt' /usr/bin/expect ./expectssh.exp $hostip $usr $pswd "$SCRIPT" 

任何build议,我可以通过我的期望脚本通过读取命令没有挂呢?

在一个侧面说明,因为我知道它会出现 – 我不能做基于密钥的自动SSHlogin。 我必须提示input用户名和密码,这是从调用此expect脚本的Korn shell脚本完成的。

感谢您的任何build议和帮助,您可以提供!

对于任何感兴趣的人来说,我可以通过做一些事情来获得read命令来为用户输入工作:

(1)在输入密码后,将它放在-re $prompt块内,而不是追加send -- "$commands\r"

(2)将命令硬编码到脚本中而不是传入脚本。

(3)使用interact语句执行命令,以便在用户响应之前不会输入下一个发送命令。

我的期望块现在看起来像这样:

 expect { -re "(.*)assword:" { send -s "$pswd\r" exp_continue } "denied, please try again" { send_user "Invalid password or account.\n" exit 5 } "incorrect" { send_user "Invalid password or account.\n" exit 5 } "you sure you want to continue connecting" { send -s "yes\r" exp_continue } -re $prompt { set timeout -1 send -- "hostname > partnerinit\r" expect -exact "hostname > partnerinit\r" send -s "netstat -rn\r" expect -re "$prompt" send -- "read n_card?'Enter the network interface card number for this server (ie eth0): '\r" interact "\r" return send -- "\r" send -- "echo \$n_card >> partnerinit\r" send -- "msk=\$(cat /etc/sysconfig/network-scripts/ifcfg-\$n_card | grep NETMASK)\r" send -- "msk=\$(echo \${msk#NETMASK=})\r" send -- "echo \$msk >> partnerinit\r" send -- "cat partnerinit\r" set retval 0 } timeout { send_user "Connection to host $host timed out.\n" exit 10 } eof { send_user "Connection to host $host failed.\n" exit 1 } } 

我还更新了脚本,以便根据用户输入的网络接口卡号自动确定子网掩码。 引起我的注意的是,在具有多个接口卡的盒子的情况下,找到网络接口卡号将是非常难以自动化的。 最好从小开始,让用户在整个脚本运行后稍后输入并进行微调/自动化。

现在我正在修改这个脚本,以便将我的partnerinit文件返回到本地主机,并从每个期望条件返回有意义的退出状态。