Shell主要使用的就是expect工具,它可以通过向进程发送命令从而达到非交互的方式去登录设备并在登录设备上执行语句

expect工具有几个相关的语法格式:

spawn

在它的后面跟上在shell中执行的语句,在expect解释的过程中是不能直接使用shell中的命令的

expect

expect表示期望在屏幕遇到什么样的内容,我们使用expect指出我们遇到什么样的内容之后,才能再指定用该工具输入什么样的内容

send

当我们使用expect指定了希望遇到的内容之后,就需要使用send然后在后面加上我们需要输入的内容,这样就可以实现非交互的脚本运行

set timeout n      

设置多久算作超时,超时之后就不再等待内容的反馈,默认是-1,也就是一直等待

interact           

别人说是将控制权返回给用户,但是我在远程登录的一些情况的时候,这个脚本就执行不了了,直接回到原来的shell

expect eof       

放在结尾,表示结束,脚本结尾一定要加这个!!!

set   变量   值

设置变量,我们 使用$变量名的方式调用变量

在bash脚本中,我们使用$1,$2的方式去使用启动脚本时加入的参数

在expect脚本中,我们使用set 变量 [lindex $argv n]  的方式去使用启动脚本时加入的参数 

脚本案例

shell脚本登录harbor仓库 shell脚本登录网页_shell脚本登录harbor仓库

 该例子使用while循环依次读出user文件中的IP地址,然后再依次telnet这些IP地址,然后使用dis cu命令显示它们当前的配置。 

1、spawn telnet $line :表示开启一个telnet进程,后面的$line是IP地址

2、expect "*Username*":表示期望任何包含Username的内容

3、send "fuck\r" :因为前面一句是expect "*Username*",所以当出现Username之后,它就会向这个进程输入一个fuck,也就是做用户名的输入

4、expect "*Password*" :表示期望任何包含"Password"的内容

5、send "*111*" :因为前面一句是expect "*Password*",所以当出现Password之后,它就会向这个进程输入一个111,也就是做密码的输入

6、expect "*":这一句就是只要屏幕的上有任何东西都期望,因为用户名和密码输入之后就远程登录到了系统上,所以我这里就不怎么在意屏幕现在的内容

7、send " sys\r  dis cu\r  quit\r  quit\r" :远程登录后在远程的系统上执行命令

我们可以在send后面加上多条语句,每条语句使用空格分开,但是注意每条语句的尾部都要以\r结尾,\r是回车符,就相当于输入命令时候按的回车键。send " sys\r  dis cu\r  quit\r  quit\r" 这条语句执行后,就相当于在远程系统上先进入系统视图,然后显示配置内容,然后退出系统视图,最后退出telnet登录,如果我们没有使用quit命令退出telnet远程登录,当语句执行到expect eof,也就是运行到脚本的尾部,那么将会脚本将会卡住,不接受任何的输入,一段时间后才会退出

一些感想:

如果我们使用expect非交互脚本去给网络设备去配置的话,其实脚本也不是万能的,遇到不同的网络情况,我们的脚本并不是适配所有的网络情况,所以有的时候在具体的网络设备上,命令的书写如果去依靠脚本的话并不是一个很好的选择,因为你怎么知道vlan要创建几个,哪个端口要做什么样的配置。我们更倾向于远程登录后将预先写好的配置粘贴上去,比如这个粘贴的操作就可以使用脚本去完成,就比如当我们设备比较多的时候,命令的配置这个操作就很麻烦了,所以书写多个远程登录的语句,然后在send语句后面加上我们预先写好的配置,然后运行脚本呢后就可以在多台设备上进行命令的执行了,我们就省去了去连接每一台设备的时间。

我们还可以使用这个脚本远程对设备的配置文件进行上传备份到某个文件服务器,这些都是可以实现的,而且还可以结合linux的定时任务,定时备份上传,这也是一个不错的选择。

还可以批量操作从文件服务器上下载东西。总的来说这个东西还是十分的有用的。