次のスクリプトを使用する必要があります。
# test.sh
function my_fun
{
echo "Give value for FOO"
local my_var
read my_var
export FOO=$my_var
}
# Call my_fun function
my_fun
私の殻から持ってきてください。
$ source test.sh
Give value for FOO
stackexchange
$ echo $FOO
stackexchange
Expectを使用して次のスクリプトを自動化したいと思います。
$ expect test.exp
$ echo $FOO
stackexchange
環境変数の数と名前がtest.sh
不明です。
修正する:
- test.shにすべてのmy_fun関数を追加します。
答え1
基本的な問題は、子プロセスが親プロセスの環境を変更できないことです。これが、source
環境変数が現在のシェルに保持されるようにシェルスクリプトが必要な理由です。
spawn
Expectはサブプロセスで使用するように設計されています。現在のシェルできない結果の影響を受けますexpect test.exp
。
ただし、シェルを作成し、対応するシェルスクリプトを取得して保持できます。それシェルと対話します。テストされていない私の考えは次のとおりです。
#!/usr/bin/expect -f
set timeout -1
spawn $env(SHELL)
set myprompt "some pattern that matches your prompt"
expect -re $myprompt
send "source test.sh\r"
expect {
"Give value for " {
# provide the same answer for every question:
send "some value\r"
exp_continue
}
-re $myprompt
}
interact
これで作成されたシェルと対話しています。このシェルを使用すると、exit
結果のシェルが終了し、スクリプトが終了することが予想され、初期化された変数なしで現在のシェルに戻ります。
答え2
関数を実行する前後に環境を区別するシェルスクリプトを作成できます。
#!/bin/bash
# run.sh
source ./test.sh
ENV_BEFORE=$(set | grep -v "^_")
my_fun
ENV_AFTER=$(set | grep -v "^ENV_BEFORE" | grep -v "^_")
# echo the new environment variables
echo "$ENV_AFTER" | grep -v -F -x -f <(echo "$ENV_BEFORE")
次に、予測を使用してスクリプトを実行します。
# test.exp
log_user 0
spawn ./run.sh
expect "Give value for "
expect -re "(.*)\r\n"
send -- "stackexchange\r\n"
expect -re "(.*)\r\n"
expect -re "(.*)\r\n"
puts $expect_out(1,string)
出力ソース:
$ source <(expect test.exp)
$ echo $FOO
stackexchange
答え3
spawn /bin/bash -c ". ./source_script.sh && ./exec_script.sh"