シェルスクリプトで機能するようにエクスポートコマンドを渡す

シェルスクリプトで機能するようにエクスポートコマンドを渡す
#!/bin/sh

execute_cmd()
{
   $($@)
}

execute_cmd export MY_VAR=my_val
echo ${MY_VAR}

$()サブシェルで実行されるため、$MY_VARスクリプトが実行されるシェルでは正しく設定されません。

私の質問は、エクスポートコマンドを関数に渡し、スクリプトが実行されている現在のシェルでどのように実行しますか?

ベストアンサー1

何をしたいのか明確ではありません。$($@)話すことはできませんが、あなたは何をしたいですか?

$($@)ですか:

  • 関数のパラメータを取得します。これは文字列のリストです。
  • スペースを含む各セクションをさらに分割します。
  • 各分割を取得し、ワイルドカードパターンとして解釈します。パターンがファイルと一致する場合、この部分は一致するファイル名のリストに置き換えられます。
  • 最初の部分を実行するコマンド名(関数、シェル組み込み、または実行可能ファイル)として使用し、他の部分を引数として渡します。
  • コマンドの出力を取得し、スペースを含む場所ごとに分割します。
  • 各分割を取得し、ワイルドカードパターンとして解釈します。パターンがファイルと一致する場合、この部分は一致するファイル名のリストに置き換えられます。
  • 最初の部分を実行するコマンド名(関数、シェル組み込み、または実行可能ファイル)として使用し、他の部分を引数として渡します。

これが複雑に聞こえるなら、そうだからです。

execute_cmd export MY_VAR=my_valあなたがそれを実装したいのであればexport MY_VAR=my_val、なぜ面倒になりますかexecute_cmd

これを合理的に説明する方法は2つあります。

  1. パラメータとともにコマンドを関数に渡そうとします。引数を持つコマンドは文字列のリストで、最初のものは関数名、シェル組み込み、または実行可能ファイルです。指定されたパラメータを使用してこのコマンドを呼び出す構文は次のとおりです"$@"

    execute_cmd () {
      "$@"
    }
    execute_cmd export MY_VAR=my_val
    

    二重引用符は、上記の分割とワイルドカードの拡張ステップを防ぎます。変数の置換には常に二重引用符を使用してください。

    exportまた、キーワード/組み込み機能の二重特性に注意してください。キーワードの存在により、シェルは構文export MY_VAR=$(seq 10)解析と同様に出力を割り当てることができますが、コマンドはここにないため、シェルはそれを割り当てとして解析しません。したがって、通常のコマンドの引数として解析され、分割されます。 +glob は で実行されるので、以下が必要です。seq 10$MY_VARMY_VAR=$(seq 10)exportMY_VAR=$(seq 10)execute_cmd export MY_VAR=$(seq 10)exportexecute_cmdMY_VAR=$(seq 10)$(seq 10)execute_cmd export MY_VAR="$(seq 10)"

  2. シェルピースを実行したいです。シェルフラグメントは、単一の引数として渡される単一の文字列です。シェルコードを含む文字列を実行するには、eval組み込み関数を使用します。

    execute_cmd () {
      eval "$1"
    }
    execute_cmd 'export MY_VAR=my_val'
    

デフォルトでは1と仮定されますIFS。これを知っていれば、この段落を読む必要はありません。

おすすめ記事