expect实现自动交互由浅入深

expect实现自动交互由浅入深,第1张

概述expect实现自动交互由浅入深作为运维人员可以通过Shell可以实现简单的控制流功能,如:循环、判断等。但是对于需要交互的场合则必须通过人工来干预,有时候我们可能会需要实现和交互程序如telnet服务器等进行交互的功能。而Expect就使用来实现这种功能的工具。Expect是一个免费的编程工具语言,用来实现自动和交互式任务进行通信,而无需人的干预。安装expect,直接yum install expect -yexpect中相关命令命令解释spawn启动新的进程send用于向进程发送字符串expect从进程接收字符串interact允许用户交互exp_continue匹配多个字符串在执行动作后加此命令一般步骤:启动expect进程(spawn)--> 接收进程字符串(expect) --> 匹配字符串,成功发送字符串(send),否则等待 --> 结束好了就直接步入主题吧,不扯那些没用的。直接上实例:一. 入门例子:实现自动登录[root@localhost shell.sh]# vim test.exp#!/usr/bin/expectset timeout 30spawn ssh -l root 192.168.1.106expect {"(yes/no)?" { send "yesr" }"password:" { send "jiajier" }}interact参数解释#!/usr/bin/expect说明使用的shell环境set timeout 30设置超时时间,单位为秒,-1为没有限制spawn ssh...需要执行的命令,这里是ssh登陆命令expect "(yes/no)?"判断上次输出结果里是否包含(yes/no)?的字符串send "yesr"执行交互动作,接轨上一个命令,如果上面的expect执行成功,则发送yesinteract执行完成后保持交互状态,把控制权交给控制台执行该实例:./test.exp如果报错-bash: ./test.exp: Permission denied,给744权限即可。二. 使用变量:[root@localhost shell.sh]# vim test.exp#!/usr/bin/expectset ip 192.168.1.106set user rootset password jiajieset timeout 30spawn ssh -l $user $ipexpect {"(yes/no)?" { send "yesr";exp_continue }"password:" { send "$passwordr" }}interactset:设置变量,后面直接变量,通过“$变量名”来调用三. 使用位置参数:[root@localhost shell.sh]# vim test.exp#!/usr/bin/expectif {$argc!=3} {send_user "Usage:expect need three arguments:ip user passwordn"exit 1}set ip [lindex $argv 0]set user [lindex $argv 1]set password [lindex $argv 2]set timeout 30spawn ssh -l $user $ipexpect {"(yes/no)?" { send "yesr";exp_continue }"password:" { send "$passwordr" }}interact[lindex $argv num]:表示位置参数,从num=0开始send_user: 打印当前提示,相当于shell里的echo.四. 执行多个命令:[root@localhost shell.sh]# vim test.exp#!/usr/bin/expectif {$argc!=3} {send_user "Usage:expect need three arguments:ip user passwordn"exit 1}set ip [lindex $argv 0]set user [lindex $argv 1]set password [lindex $argv 2]set timeout 30spawn ssh -l $user $ipexpect {"(yes/no)?" { send "yesr";exp_continue }"password:" { send "$passwordr" }}expect "]#" { send "useradd jjr" }expect "]#" { send "echo jiajie|passwd --stdin jjr" }send "exitr"expect eofexit -onexit {send_user "useradd jj is successfully.n"send_user "Jobs has finished,Goodbye.n"}执行后的结果输出:[root@localhost shell.sh]# ./test.exp 192.168.1.106 root jiajiespawn ssh -l root [email protected]'s password:Last login: Sat Sep 9 03:47:48 2017 from web[root@localhost ~]# useradd jj[root@localhost ~]# echo jiajie|passwd --stdin jjChanging password for user jj.passwd: all authentication tokens updated successfully.[root@localhost ~]# exitlogoutConnection to 192.168.1.106 closed.useradd jj is successfully.Jobs has finished,Goodbye.send "exitr":登录出当前环境。expect eof:结束expect匹配。exit -onexit{...}:打印结束的提示信息。五. shell脚本调用expect(1)[root@localhost shell.sh]# vim test.sh#!/bin/baship=$1user=$2password=$3expect <<EOFset timeout 10spawn ssh -l $user $ipexpect {"yes/no" { send "yesn";exp_continue }"password" { send "$passwordn" }}expect "]#" { send "useradd jjn" }expect "]#" { send "echo jiajie|passwd --stdin jjn" }expect "]#" { send "exitn" }expect eofEOF执行后的输出结果:[root@localhost shell.sh]# ./test.sh 192.168.1.106 root jiajiespawn ssh -l root [email protected]'s password:Last login: Sat Sep 9 04:10:46 2017 from web[root@localhost ~]# useradd jj[root@localhost ~]# echo jiajie|passwd --stdin jjChanging password for user jj.passwd: all authentication tokens updated successfully.[root@localhost ~]# exitlogoutConnection to 192.168.1.106 closed.[root@localhost shell.sh]#五. shell脚本调用expect(2)通过shell脚本通过调用expect脚本实现批量认证:expect脚本:[root@localhost shell.sh]# vim scp.exp#!/usr/bin/expectif {$argc!=3} {send_user "Usage:expect need three arguments lisk thks:file host dirn"exit 1}set srcname [lindex $argv 0]set hostname [lindex $argv 1]set destname [lindex $argv 2]set password "jiajie"spawn scp $srcname root@$hostname:$destnameset timeout 30expect {# -timeout 2"yes/no" {send "yesr";exp_continue}"*password:" {send "$passwordr"}# timeout {puts "expect connect failure,please contact admin.";return}}expect eofexit -onexit {send_user "Jobs has finished,Goodbye.n"}shell脚本:[root@localhost shell.sh]# vim scp.sh#!/bin/bashif [[ "$#" != "2" ]];thenecho "Usage:$0 src_filename des_filename"exit 0fiIP_LIST=(192.168.1.106192.168.1.170192.168.1.10). /etc/init.d/functionsfor ip in ${IP_LIST[*]}doexpect scp.exp $1 $ip $2 &> /dev/nullif [ $? -eq 0 ];thenaction "$ip" /bin/trueelseaction "$ip" /bin/falsefidonescp.sh脚本通过调用expect脚本来实现分发功能。执行结果如下:[root@localhost shell.sh]# sh scp.sh /etc/fstab /tmp/192.168.1.106 [ OK ]192.168.1.170 [ OK ]192.168.1.10 [FAILED]因为并没有192.168.1.10所有

<h1 ID="expect实现自动交互由浅入深">expect实现自动交互由浅入深

作为运维人员可以通过Shell可以实现简单的控制流功能,如:循环、判断等。但是对于需要交互的场合则必须通过人工来干预,有时候我们可能会需要实现和交互程序如telnet服务器等进行交互的功能。而Expect就使用来实现这种功能的工具。Expect是一个免费的编程工具语言,用来实现自动和交互式任务进行通信,而无需人的干预。

安装expect,直接yum install expect -y

命令解释一般步骤:

启动expect进程(spawn)--> 接收进程字符串(expect) --> 匹配字符串,成功发送字符串(send),否则等待 --> 结束

好了就直接步入主题吧,不扯那些没用的。直接上实例:

[root@localhost shell.sh]# vim test.exp#!/usr/bin/expectset timeout 30spawn ssh -l root 192.168.1.106expect {"(yes/no)?" { send "yes\r" }"password:" { send "jiajIE\r" }}interact
参数解释执行该实例:./test.exp

如果报错-bash: ./test.exp: Permission denIEd,给744权限即可。

[root@localhost shell.sh]# vim test.exp

#!/usr/bin/expectset ip 192.168.1.106set user rootset password jiajIEset timeout 30spawn ssh -l $user $ipexpect {"(yes/no)?" { send "yes\r";exp_continue }"password:" { send "$password\r" }}interact

set:设置变量,后面直接变量,通过“$变量名”来调用

[root@localhost shell.sh]# vim test.exp !/usr/bin/expect

if {$argc!=3} {
send_user "Usage:expect need three arguments:ip user password\n"
exit 1
}
set ip [lindex $argv 0]
set user [lindex $argv 1]
set password [lindex $argv 2]
set timeout 30
spawn ssh -l $user $ip
expect {
"(yes/no)?" { send "yes\r";exp_continue }
"password:" { send "$password\r" }
}
interact

[lindex $argv num]:表示位置参数,从num=0开始

send_user: 打印当前提示,相当于shell里的echo.

[root@localhost shell.sh]# vim test.exp !/usr/bin/expect

if {$argc!=3} {
send_user "Usage:expect need three arguments:ip user password\n"
exit 1
}
set ip [lindex $argv 0]
set user [lindex $argv 1]
set password [lindex $argv 2]
set timeout 30
spawn ssh -l $user $ip
expect {
"(yes/no)?" { send "yes\r";exp_continue }
"password:" { send "$password\r" }
}
expect "]#" { send "useradd jj\r" }
expect "]#" { send "echo jiajIE|passwd --stdin jj\r" }
send "exit\r"
expect eof
exit -onexit {
send_user "useradd jj is successfully.\n"
send_user "Jobs has finished,Goodbye.\n"
}

执行后的结果输出:

[root@localhost shell.sh]# ./test.exp 192.168.1.106 root jiajIEspawn ssh -l root [email protected]'s password: Last login: Sat Sep  9 03:47:48 2017 from web[root@localhost ~]# useradd jj[root@localhost ~]# echo jiajIE|passwd --stdin jjChanging password for user jj.passwd: all authentication tokens updated successfully.[root@localhost ~]# exitlogoutConnection to 192.168.1.106 closed.useradd jj is successfully.Jobs has finished,Goodbye.

send "exit\r":登录出当前环境。

expect eof:结束expect匹配。

exit -onexit{...}:打印结束的提示信息。

[root@localhost shell.sh]# vim test.sh!/bin/bash

ip=$1
user=$2
password=$3
expect <<EOF
set timeout 10
spawn ssh -l $user $ip
expect {
"yes/no" { send "yes\n";exp_continue }
"password" { send "$password\n" }
}
expect "]#" { send "useradd jj\n" }
expect "]#" { send "echo jiajIE|passwd --stdin jj\n" }
expect "]#" { send "exit\n" }
expect eof
EOF

执行后的输出结果:

[root@localhost shell.sh]# ./test.sh 192.168.1.106 root jiajIEspawn ssh -l root [email protected]'s password: Last login: Sat Sep  9 04:10:46 2017 from web[root@localhost ~]# useradd jj[root@localhost ~]# echo jiajIE|passwd --stdin jjChanging password for user jj.passwd: all authentication tokens updated successfully.[root@localhost ~]# exitlogoutConnection to 192.168.1.106 closed.[root@localhost shell.sh]# 

通过shell脚本通过调用expect脚本实现批量认证:

expect脚本:

[root@localhost shell.sh]# vim scp.exp!/usr/bin/expect

if {$argc!=3} {
send_user "Usage:expect need three arguments lisk thks:file host dir\n"
exit 1
}
set srcname [lindex $argv 0]
set hostname [lindex $argv 1]
set destname [lindex $argv 2]
set password "jiajIE"
spawn scp $srcname root@$hostname:$destname
set timeout 30
expect {

-timeout 2
    "yes/no" {send "yes\r";exp_continue}    "*password:" {send "$password\r"}
timeout {puts "expect connect failure,please contact admin.";return}

}
expect eof
exit -onexit {
send_user "Jobs has finished,Goodbye.\n"
}

shell脚本:

[root@localhost shell.sh]# vim scp.sh !/bin/bash

if [[ "$#" != "2" ]];then
echo "Usage:$0 src_filename des_filename"
exit 0
fi
IP_List=(
192.168.1.106
192.168.1.170
192.168.1.10
)
. /etc/init.d/functions
for ip in ${IP_List[*]}
do
expect scp.exp $1 $ip $2 &> /dev/null
if [ $? -eq 0 ];then
action "$ip" /bin/true
else
action "$ip" /bin/false
fi
done

scp.sh脚本通过调用expect脚本来实现分发功能。执行结果如下:

[root@localhost shell.sh]# sh  scp.sh  /etc/fstab /tmp/192.168.1.106                                              [  OK  ]192.168.1.170                                              [  OK  ]192.168.1.10                                               [Failed]

因为并没有192.168.1.10所有报错。

总结

以上是内存溢出为你收集整理的expect实现自动交互由浅入深全部内容,希望文章能够帮你解决expect实现自动交互由浅入深所遇到的程序开发问题。

如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。

欢迎分享,转载请注明来源:内存溢出

原文地址: https://outofmemory.cn/yw/1050574.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-05-25
下一篇 2022-05-25

发表评论

登录后才能评论

评论列表(0条)

保存