在开发过程中,编译部署都是无法避免的步骤,但是在调试时,需要重复地进行编译部署,如果这个过程复杂,那就更加耗时费力。重复劳作是枯燥的,所以大多数情况下,我们可以使用expect来进行自动化交互过程,从而自动化整个编译和部署过程。

首先需要安装expect

apt install -y expect

Expect语言是基于Tcl的。Tcl实际上是一个子程序库,这些子程序库可以嵌入到程序里从而提供语言服务。其实expect常用的命令只有spawn,send,expect。下面用一个自动修改Ubuntu密码的例子来说明如何使用expect

#!/usr/bin/expect

spawn passwd
expect "*password:"
send "123\r"
expect "*password:"
send "123\r"

expect eof

第一行以spawn启动passwd程序。在第二行,expect搜索模式”*password:”,其中*允许匹配任意输入,所以对于避免指定所有细节而言是非常有效的。一旦接收到提示后,下一行就就把密码123送给当前进程,\r表明回车。上面的程序中有两个expect-send序列,因为passwd为了对输入进行确认,要求进行两次输入。最后,expect eof这一行的作用是在passwd的输出中搜索文件结束符,这一行语句还展示了关键字的匹配。在这里eof是有必要的,因为passwd被设计成会检查它的所有I/O是否都成功了,包括第二次输入密码时产生的最后一个新行。

在使用expect时,需要注意的是,常规.sh文件,开头都是#!/bin/bash,但是使用expect.sh文件第一行都是#!/usr/bin/expect。这也说明,常规的shell或者bash命令都无法使用。所以,在使用过程中,建议把每个需要交互的模块单独写成一个单独的sh文件,最后写一个汇总的常规bash文件来一次性执行所有命令。例如,上面的例子,可以写成一个setup-password.sh,然后可以再写一个总的setup.sh来调用setup-password.sh

#!/bin/bash
setup-password.sh