命令放入 Expect 时未按应有的顺序显示消息

命令放入 Expect 时未按应有的顺序显示消息

我有一些脚本可以自动化流程,我希望有关我所处步骤的消息显示在命令窗口中。我有一段代码是:

puts "** Creation of $VMNAME on $HOST begins... **"
spawn ssh -l $USER $HOST
expect_after eof {exit 0}
set timeout 10

expect "(yes/no)?" { send "yes\r" }
expect "password:" { send "$PASSWORD\r" }
expect "~]#" { send "date\r" }
set timeout 1200

puts "** Transferring rhelvm img file to the $HOST... **"
expect "~]#" { send "scp  somelink/rhelvm-0-vol.img /storage/iso/\r" }
expect "Password:" { send "$TESTEMSPASS\r" }

puts "** Transferring the VM conf from $TESTEMSUSER to $HOST... **"
expect "~]#" { send "scp somelink/$VMNAME.conf /root\r" }
expect "Password:" { send "$TESTEMSPASS\r" }

puts "** Removing the $VMNAME... **"
expect "~]#" { send "/opt/ccm/bin/vmremove -f /root/$VMNAME.conf --force\r" }
sleep 10
expect "~]#" { send "rm -rf /storage/vmpool/*.img\r" }
sleep 10

puts "** Creating the $VMNAME... **"
expect "~]#" { send "/opt/ccm/bin/vmcreate -f /root/$VMNAME.conf -g  /storage/iso/rhelvm-0-vol.img -e\r" }
sleep 10

puts "** Starting the $VMNAME ... **"
expect "~]#" { send "virsh start $VMNAME\r" }
sleep 10

expect "~]#" { send "virsh list --all\r"}

expect "~]#" { send "date\r" }

puts "** Creation of $VMNAME is completed. **"
expect "~]#" { send "exit\r" }

但我在输出中得到的内容并不是按此顺序排列的,例如它显示创建虚拟机的消息,但随后运行 rm -rf /storage/vmpool/*.img 命令。我尝试使用 -nonewline 和 send_user 进行 put,但似乎没有任何效果。请帮我!!

答案1

之后send "cmd\r"expect 将其发送send<CR>到控制 ssh 进程的伪终端设备的主端。

然后从从机端ssh读取 acmd<LF>并将其发送到远程主机,最终到达远程主机,然后 shell 再次读取它。

远程伪终端设备的 shell 或线路规则发回一个cmd<CR><LF>用于显示(虚拟输入的文本的)的 ,并最终使其返回到用于控制的echo伪终端的主端。expectssh

但仅根据指令expect处理该内容(其输出ssh包括) 。所以在echoexpect

send "cmd\r"
sleep 4
puts "text"
expect "output of ssh" {...}

text输出回声cmd, 因为那回声仅显示在 上expect

你可以这样做:

send "cmd\r"
expect "cmd\r\n" # wait for the echo (or just expect "\n")
sleep 4
puts "text"
expect "output of ssh (next prompt)" {...}

首先等待该命令的回显。或者:

send "cmd\r"
sleep 4
expect "output of ssh (next prompt)" {puts "text"; ...}

然后text在下一个提示时显示 。

答案2

您可能需要刷新输出文件。每次puts添加行后

 flush stdout

参见tcl冲水命令。或者,您可以使用一行将输出设置为非缓冲模式:

 fconfigure stdout -buffering none

参见tcl配置

相关内容