2014-03-03 115 views
0

我使用下面的expect腳本的SSH遠程登錄樹莓派和執行命令期待SSH遠程登錄腳本和執行命令

#!/usr/bin/expect 
set timeout 60 
spawn ssh [lindex $argv 1]@[lindex $argv 0] 
expect "yes/no" { 
    send "yes\r" 
    expect "*?assword" { send "[lindex $argv 2]\r" } 
    } "*?assword" { send "[lindex $argv 2]\r" } 
expect "[email protected] ~ $ " { 
    send "ls -la\r" 
    } 
interact 

的問題是,這個腳本能夠登錄到覆盆子,但是當它爲了執行「ls -la」命令而行,什麼也沒有發生。任何人都可以幫我解決這個腳本?我在哪裏犯錯?

確定的,如果我把

exp_internal 1

線在我的劇本我獲得以下的地方匹配輸出失敗

期待:執行「:\ r \ nLinux raspberrypi 3.10.24以上#614 PREEMPT Thu Dec 19 20:38:42 GMT 2013 armv6l \ r \ n \ r \ n Debian GNU/Linux系統附帶的程序是免費軟件;每個程序的準確分配條款被描述在該\ r \在/usr/share/doc/*/copyright.\r\n\r\nDebian GNU/Linux的nindividual文件帶有絕對沒有擔保,適用法律npermitted程度\ r \。\ r \ n上次登錄:星期一03月03日19點00分11秒2014從192.168.1.200 \ r \ r \ n \ u001b] 0; PI @樹莓派:〜\ u0007 \ u001b [01; 32mpi @樹莓派\ u001b [00米\ u001b [01; 34m〜$ \ u001b [00m「(spawn_id exp6)匹配glob模式」* pi @ raspberrypi〜$ *「?沒有

應該不是這種匹配是真的嗎?

+0

另一種選擇是啓用基於密鑰的登錄到您的Pi,以便您不必擔心密碼。然後你可以運行'ssh pi.ip.address ls -la'。 – larsks

+0

我無法使用基於密鑰的登錄,他們必須是基於密碼的登錄。 – prattom

回答

6

您應該使用exp_continue重新輸入您的期望環路密碼和真實性檢查完成後,請嘗試以下:

#!/usr/bin/expect 

set prompt "[email protected] ~ $ " 
spawn ssh [lindex $argv 1]@[lindex $argv 0]               

set timeout 5 
expect { 
    timeout { 
     puts "Connection timed out" 
     exit 1 
    } 

    "yes/no" { 
     send "yes\r" 
     exp_continue 
    } 

    "assword:" { 
     send -- "[lindex $argv 2]\r" 
     exp_continue 
    } 

    "$prompt" { 
     send "ls -la\r" 
    } 
} 

這是探索期待和由多恩·利伯斯exp_continue採取的摘錄:

當作爲預期動作執行時,所述指令exp_continue使控制電流期望命令內部繼續進行。期望繼續嘗試匹配模式,但從之前的比賽結束後停止。期望有效地重複搜索,就好像它再次被調用一樣。

3

你可能有一個看看這個......它需要命令的列表,包含在文件中,並通過交互式登錄和 執行它們一個在-A-時間執行它們在遠程主機上在遠程機器上。您可以打開日誌 如果你想捕獲輸出,你會需要調整它來處理您的 計算機(或其他設備的)提示:

 

    #!/usr/bin/expect 
    # 
    # Read a list of commands and execute them on remote host 
    # 
    # WA2IAC 3/9/2015 
    # 

    spawn ssh -l username target_host 
    expect "ord\\: " 
    send "your_password\r" 
    set handle [ open commandfile.txt r ] 
    while { ! [eof $handle] } { 
     gets $handle buf 
     expect "\\$" 
     send "$buf\r" 
     } 
    interact 

您可以通過設置超時充實了這一點,處理可能出錯的事情(請參閱上面的代碼片段)。刪除「interact」語句以在腳本完成時退出(您可以使用shell循環對多個主機/設備執行此操作)。

我用這個命令發送路由器更新靜態路由,但它有許多其他用途。我是從這裏:http://wa2iac.com/wiki/index.php?title=Expect_remote_commands

0

我還建議確保您期待由你上次發送命令使用期望命令時輸出的最後一個字符串模式。我告訴你這是因爲Expect的輸出保存在緩衝區中,緩衝區只能保存這麼多的數據。我在這個問題上摔了一會兒,沒有找到爲什麼我的expect -re {}命令沒有被正確拾取,我期待着前一個發送命令輸出的前幾個字符串模式。我應該一直在尋找最後一個String模式,因爲這個String模式肯定在Expect的緩衝區中,並且第一個字符串已經被刪除,因爲緩衝區只能容納這麼多的數據。我發送命令的輸出有點長。