expect是一款自動化的腳本解釋型的工具。它基于tcl腳本,其運行需要tcl的支持。expect對一些需要交互輸入的命令很有幫助,比如ssh ftp scp telnet。
創(chuàng)新互聯(lián)是一家專業(yè)提供息縣企業(yè)網(wǎng)站建設(shè),專注與成都網(wǎng)站制作、成都網(wǎng)站建設(shè)、外貿(mào)營銷網(wǎng)站建設(shè)、H5技術(shù)、小程序制作等業(yè)務(wù)。10年已為息縣眾多企業(yè)、政府機構(gòu)等服務(wù)。創(chuàng)新互聯(lián)專業(yè)網(wǎng)站設(shè)計公司優(yōu)惠進行中。
在遠程登錄linux服務(wù)器的時候,ssh命令需要手工輸入密碼,當?shù)卿浂嗯_機器的時候就會非常繁瑣。expect就可以根據(jù)設(shè)定的規(guī)則,自動幫我們輸入密碼,大大節(jié)省了時間。
通常系統(tǒng)中不會安裝expect,需要手動進行安裝
系統(tǒng)為Centos時:
yum install expect -y
Timeout:指定超時時間,默認為10s
? 當timeout -1時代表永不超時
Send:向進程發(fā)送字符串,模擬用戶輸入
? 通常后面會跟“\r”代表回車換行
Spawn:啟動進程,并追蹤后續(xù)命令
Expect:對進程進行捕捉(只能捕捉spawn啟動的進程)
? 判斷上次輸出結(jié)果里是否包含指定的字符串
Interact:將控制權(quán)交回控制臺
$argv參數(shù)數(shù)組:接受從bash傳遞的參數(shù)
? 參數(shù)從0開始,代表第一個參數(shù)
分為兩種主要執(zhí)行方式:直接在expect解釋器中進行執(zhí)行、結(jié)合“<<”下一位的分界符進行嵌入執(zhí)行。
[root@localhost~]#more a.sh
#!/usr/bin/expect //導入expect解釋器
set timeout 20 //20秒超時時間
set hostname [lindex $argv 0] //追加參數(shù)0,加載第1位置
set password [lindex $argv 1] //追加參數(shù)1,加載第2位置
spawn ssh root@$hostname
expect {
"(yes/no)" //捕獲關(guān)鍵字
{send"yes/r";exp_continue} //輸入yes,繼續(xù)下一步
"*password" //參數(shù)2
{send"$password\r"} //模擬人工輸入
}
interact //交回控制權(quán)回終端
這里解釋一下“<<”的用法:
? 當shell看到“<<”的時候,它就會知道下一個詞是一個分界符。在該分界符以后的內(nèi)容都被當作輸入,直到shell又看到該分界符(位于單獨的一行)。這個分界符可以是你所定義的任何字符串。
“EOF”與“-EOF”兩種分界符的不同:
? “EOF”沒有容錯率,一旦結(jié)尾的分界符存在空格或者制表符,就會導致腳本報錯。
? “-EOF”有一定的容錯率,結(jié)尾的分界符可以允許存在制表符。
[root@localhost~]#more b.sh
#!/bin/bash //導入bash解釋器
hostname=$1
password=$2
/usr/bin/expect<<-EOF //將EOF作為分界符,下面所有操作均停留在當前終端
spawn ssh root@${hostname} //啟動進程,開始追蹤ssh命令
expect {
"(yes/no)"
{send "yes\r";exp_continue}
"*password"
{send"$password\r"}
}
expect "*]#"
send "exit\r"
expect eof //等待分界符結(jié)束
EOF //另一位分界符,代表操作結(jié)束
直接執(zhí)行Demo
#!/usr/bin/expect
#超時時間
set timeout 20
log_file test.log
log_user 1
#參數(shù)傳入
set hostname [lindex $argv 0]
set password [lindex $argv 1]
#追蹤命令
spawn ssh root@$hostname
#捕捉信息并且匹配,免交互執(zhí)行
expect {
"Connection refused" exit
"service not known" exit
"(yes/no)"
{send "yes\r";exp_continue}
"*password"
{send "$password\r"}
}
#控制權(quán)交給控制臺執(zhí)行
interact
exit
效果如下
嵌入執(zhí)行Demo
#!/bin/bash
user=$1
password=$2
#非交互命令放在expect外
useradd $user
#開始進行交互
expect <<-EOF
spawn passwd $user
expect "新的*"
send "${password}\r"
expect "重新*"
send "${password}\r"
expect eof;
EOF
#以上為腳本實際內(nèi)容
效果如下: