转载:shell expect实战实例

shell expect
一个自动化交互的软件,常用场景:在回车后需要输出一些内容
批量传输文件,批量远程命令执行,修改密码,安装软件

一、安装 expect程序

yum -y install expect

二、expect 变量

1、赋值变量

set 变量名 变量值

set ip 192.168.10.3
$ip 引用赋值变量

2、位置变量

[lindex $argv 0] 第1位参数
[lindex $argv 1] 第2位参数

执行时 必须指定两个参数

3、特别注意:

  1. expect的脚本,必须赋予执行权限 a+x / +x

  2. expect不能用sh来执行,不能用source执行。只可以用 ./路径执行。

三、expect格式

exp_continue:如果后面还有要匹配的参数采用此句表示暂不跳出

\r 确定,回车(表示肯定)
interact 停止在结束位置,什么都不做

expect {

​		"遇到的内容"	{  send  "传递的参数\r";  exp_continue  }
​		"遇到的第二个内容" {  send "传递的参数\r"  };

}
#interact 		停在当前所处位置
expect eof		结束

四、bash脚本中嵌套expect

expect << EOF
cmd
EOF

或者

/usr/bin/expect << EOF
cmd
EOF

或者

/usr/bin/expect << !
cmd
!

案例1:expect 实现ssh交互式登录

#!/bin/expect

set ip 192.168.10.3
set user root
set passwd 123.com

#spawn 开启一个会话,开启一个指令
spawn ssh $user@$ip

expect {
	#如果出现 “yes/no”,则用send传参“yes\r”,\r回车,然后 continue是为没有出现yes时,跳过继续执行一下步。
        "yes/no" { send "yes\r"; exp_continue}
        "password" {send "$passwd\r"};
}
#停在对端
interact

执行:

expect ./ssh_expect.sh
spawn ssh root@192.168.10.2
root@192.168.10.2’s password:
Last login: Mon Apr 6 16:49:34 2020 from 192.168.10.225

案例2:expect传参 实现ssh交互式登录并执行命令

#!/bin/expect
#传入的第一个参数
set ip [lindex $argv 0]
#传入的第二个参数
set user [lindex $argv 1]
set passwd 123.com

spawn ssh $user@$ip

expect {
        "yes/no" { send "yes\r"; exp_continue}
        "password" {send "$passwd\r"};
}
#interact,后面不建议再添加其他匹配内容	
#到了对端后,匹配root用户的#号,还可以继续执行命令
expect "#"	
send "useradd yangyang\r"
send "pwd\r"
send "exit\r"
#expect eof 结束语句
expect eof

执行脚本
[root@localhost shell]# ./ssh_expect.sh 192.168.10.3 root

案例3:expect 实现scp文件传递

#!/bin/expect
#传入一个IP地址的参数
set ip [lindex $argv 0]
set user root
set password 123.com
set timeout 5

spawn scp -r /etc/hosts $user@$ip:/tmp

expect {
        "yes/no" { send "yes\r"; exp_continue }
        "password" { send "$password\r" };
}
#interact
expect eof

执行脚本
[root@localhost shell]# ./ssh_expect.sh 192.168.10.3

案例4:expect 实现 ssh 公钥推送

#!/usr/bin/bash

>ip.txt #清空ip.txt文件
password=123.com


#测试expect是否安装
rpm -q expect &> /dev/null
if [ $? -ne 0 ];then
        yum -y install expect &> /dev/null && \        echo -e  "\e[1;32m expect 安装成功 \e[0m"
fi

#测试是否存在私钥
if [ ! -f ~/.ssh/id_rsa ];then
        ssh-keygen -P "" -f ~/.ssh/id_rsa && \
        echo -e "\e[1;32m id_rsa 创建结束 \e[0m"
fi



for i in {1..5}
do
        {
        ip=192.168.10.$i
        ping -c1 -W1 $ip &> /dev/null
        if [ $? -eq 0 ];then
                echo "正在向$ip 传送公钥..." >> /tmp/ip.txt
                #通过<<-EOF EOF 执行expect语言
                /usr/bin/expect <<-EOF
                #spawn开启一个会话
                spawn ssh-copy-id $ip
                expect {
                        "yes/no" {send "yes\r"; exp_continue}
                        "password:" {send "$password\r"}
                }
                expect eof
                EOF
                #EOF结束expect语言

        else
                echo "该主机尚未存活"
        fi
        }&
done

————————————————
版权声明:本文为CSDN博主「 清欢渡.」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/shm19990131/article/details/106190738

posted @ 2021-03-29 14:09  彬在俊  阅读(110)  评论(0编辑  收藏  举报