Shell 腳本常需與互動式程式(ftp、telnet、passwd、su 等)自動對話。本文系統整理三種主流自動交互技術——Here Document(重導向)、Pipe(管道+sleep)、Expect 專用工具——並以實際需求場景實測比較優劣,助你按場景選對工具。
<<EOF)原理:Shell 將分隔符之間的內容作為標準輸入餵給命令。
#!/bin/bash
ftp -i -n 192.168.167.187 << EOF
user hzc 123456
pwd
cd test
pwd
close
bye
EOF
原理:用 echo 產生輸入,配合 sleep 等待程式提示,經管道傳給命令。
#!/bin/bash
(
echo "curpassword"
sleep 1
echo "newpassword"
sleep 1
echo "newpassword"
) | passwd
原理:基於 Tcl 的自動化互動套件,能模式匹配程式輸出並發送對應回應,支援分支、迴圈、逾時等完整邏輯。
#!/usr/bin/expect
spawn su root
expect "password: "
send "123456\r"
expect eof
exit
expect 套件(嵌入式環境可能無法安裝)| 維度 | Here Document | Pipe + Sleep | Expect |
|---|---|---|---|
| 依賴 | 內建 | 內建 | 需安裝 expect |
| 適用程式 | 讀 stdin 的 ftp/telnet/sftp | 簡單單向輸入的 passwd 等 | 所有(含 su、ssh、sudo) |
| 動態判斷 | 無 | 無 | 強(expect 模式匹配) |
| 穩定性 | 高(固定流程) | 低(靠 sleep) | 高 |
| 複雜度 | 低 | 低 | 中 |
lftp 或 sshpass + rsync,比 Here Document 更健壯。chpasswd 或 echo "user:pass" | chpasswd,比 Pipe 更標準。sudoers NOPASSWD;必須互動時才用 Expect。ssh-copy-id),非萬不得已勿用 Expect 存密碼。Here Document 適合固定流程的 stdin 程式;Pipe+Sleep 只能應急簡單場景;Expect 是處理複雜互動的終極武器。實務上能避免互動就避免(改用參數、金鑰、設定檔),必須互動時再按複雜度選工具。