私はbash
しばらく変数を置き換えるのに苦労しましたが、これはわかりません...
コマンドテンプレートを含む変数があります。
CMD_TMPL='sudo -u ${USER_NAME} ${USER_HOME}/script.sh'
変数USER_NAME
sumはUSER_HOME
後でスクリプトで計算され、まだ定義CMD_TMPL
されていることは知られていません。したがって、コマンドは一重引用符で囲まれており、置き換えられませんでした。
その後、スクリプトは私が含めるタスクを実行したいことUSER_NAME=test
を理解しています。USER_HOME=/home/test
${CMD}
sudo -u test /home/test/script.sh
以下のスクリプトはパイプラインでコマンドを使用します。たとえば、次のようになります。
${CMD} | output-processing.sh
変数名から${CMD_TMPL}
変数値への拡張を実装するには${CMD}
?私はいろいろなecho
ことを試しましたが、それをeval
見つけることはできません。
ありがとうございます!
答え1
コードを保存するために使用される特別な型の変数があります。機能:
cmd_tmpl() { sudo -u "$USER_NAME" "$USER_HOME/script.sh" "$@"; }
cmd() { cmd_tmpl other args "$@"; }
cmd | output_processing...
別のアプローチは、変数をコマンドライン(シェルコード)として処理し、最終的に次を使用してそのコードを解釈することですeval
。
cmd_tmpl='sudo -u "$USER_NAME" "$USER_HOME/script.sh"'
cmd=$cmd_tmpl' other args as shell code'
eval "$cmd" | output_processing...
使い方$cmd | output_processing
が間違っています。$cmd
これはスカラー変数であり、分割+glob演算子を使用して単純なコマンドの引数リストを取得すると、ここに格納されているコマンドラインを評価しません。したがって、これは限られた条件でのみ機能します。
単純なコマンドのパラメータを配列に保存できます。
cmd=(sudo -u "$USER_NAME" "$USER_HOME/script.sh" ...)
"${cmd[@]}" | post_processing
ただし、これは変数の遅延拡張には役立ちません。
次の方法で拡張を延期できます。
cmd_tmpl='sudo -u "$USER_NAME" "$USER_HOME/script.sh"'
...
eval "cmd=($cmd_tmpl)" # now expanded
cmd+=(other args)
"${cmd[@]}" | post-processing
(環境にエクスポートした変数の場合は、変数名をすべて大文字で予約するのが最善です。)