expect的安装
expect是在tcl的基础上发展起来的,所以在安装expect之前要先安装tcl。
tcl安装
wget http://nchc.dl.sourceforge.net/sourceforge/tcl/tcl8.4.11-src.tar.gz
tar -zxf tcl8.4.11-src.tar.gz
cd tcl8.4.11/unix
./configure --prefix=/usr/tcl --enable-shared
make
make install
cp tclUnixPort.h ../generic/
注意:
1、安装完毕以后,进入tcl源代码的根目录,把子目录unix下面的tclUnixPort.h copy到子目录generic中。
2、暂时不要删除tcl源代码,因为expect的安装过程还需要用。
安装expect(需tcl的库)
wget https://sourceforge.net/projects/expect/files/Expect/5.45.4/expect5.45.4.tar.gz/download --no-check-certificate -O expect5.45.4.tar.gz
tar -zxf expect5.45.4.tar.gz
cd expect5.45.4
./configure --prefix=/usr/expect --with-tcl=/usr/tcl/lib --with-tclinclude=../tcl8.4.11/generic
make
make install
ln -s /usr/tcl/bin/expect /usr/expect/bin/expect
ln -s /usr/tcl/bin/expect /usr/bin/expect
最简单的安装办法
yum list expect --showduplicates
yum install -y expect[-5.45-14.el7_1].x86_64
# 也可以先下载rpm包,然后安装
yum list expect
yum install --downloadonly --downloaddir ./ expect[-5.45-14.el7_1].x86_64
yum install -y ./*.rpm
expect的使用
示例:
#!/bin/bash
/usr/bin/expect <<-EOF
spawn ssh root@node
expect {
"connecting (yes/no)?" {exp_send "yes\r"; exp_continue}
"password:" {exp_send "root\r"}
}
expect "#"
send "hostname\r"
send "echo \\\$HOSTNAME\r"
send "exit\r"
expect eof
EOF
echo "echo $HOSTNAME"
结果:
视频教程:https://www.bilibili.com/video/BV1cV411r7jW?p=37
推荐阅读:
https://www.jianshu.com/p/32de653aa05ahttps://blog.csdn.net/yifan850399167/article/details/80845031
https://blog.csdn.net/u013163551/article/details/117977204?utm_medium=distribute.pc_5.no_search_link&
https://www.cnblogs.com/lixigang/articles/4849527.html
expect简单用法
#!/usr/bin/expect -f
set timeout 60 #设置超时时间
log_file test.log #设置脚本日志
log_user 1 #是否显示脚本输出信息 1代表显示,0代表不显示
set hostname [lindex argv 0] #接收第一个参数
set password [lindex argv 1]
spawn ssh root@$hostname #连接远程机器
expect {
"(yes/no)"
{
send "yes\r"
expect "*password:" {send "$password\r"}
}
"*password"
{
send "$password\r"
}
}
send "echo ==\$(rpm -qa | grep mariadb)==\r"
expect -re "==.*==.*==(.*)=="
set mariadb $expect_out(1,string)
expect "*]#"
send "rpm -e --nodeps $mariadb\r"
expect "*]#"
send "exit\r"
expect eof
上述代码即为一个简单的expect脚本,登录到远程机器并卸载mariadb,expect中最常用的就是”expect”和“send”命令。
expect “pattern”
send “command\r”
当远程机出现了匹配”pattern”的字符串,就执行”command”命令,在执行完命令之后别忘了加上回车符,如此便可实现自动输入密码等一系列功能。
shell嵌套expect
#!/bin/bash
hostname=$1 #接收第一个参数
password=$2
/usr/bin/expect <<-EOF # 重定向到expect
spawn ssh root@${hostname}
expect {
"(yes/no)"
{
send "yes\r"
expect "*assword:" {send "$password\r"}
}
"*assword"
{
send "$password\r"
}
}
expect "*]#"
send "echo 'export MAVEN_HOME=/usr/local/maven' >> /etc/profile\r"
send "echo 'export M2_HOME=\\\$MAVEN_HOME' >> /etc/profile\r"
send "echo 'export PATH=\\\$PATH:\\\$MAVEN_HOME/bin' >> /etc/profile\r"
expect "*]#"
send "source /etc/profile\r"
expect "*]#"
send "exit\r"
expect eof
EOF #结束重定向
expect常见问题
1、expect脚本中source命令不起作用?
shell脚本中嵌套expect脚本,再编写source命令即可正常使用
2、shell嵌套expect脚本中$expect_out(1,string)无法获得匹配字符串?
单纯使用expect脚本即可正常获取
3、shell嵌套expect脚本中对字符转义需要三个反斜杠,expect脚本中对字符转义只需要一个反斜杠。