エイリアス定義で Bash 関数を呼び出す

エイリアス定義で Bash 関数を呼び出す

私はXilinx ISEを使用しており、プログラムはすべてのツールへのパスを設定するためにベンダースクリプトをインポートする必要があります。このスクリプトはシェルの一部の機能を損なうため、シェルの起動時にインポートしたくなく、必要なときにのみインポートしたいと思います。

source /long/path/to/script便宜上、プログラムが提供するツールがインストールスクリプトなしで常に機能することを望みます。アイデアは、以下のようにn個のプログラムのそれぞれにエイリアスを持つことです(たとえば、名前がp1、...、pnであるとします)。

alias p1='source /long/path/;unalias p1;...;unalias pn;p1'

プログラムが多いので、unaliasチェーンの更新を簡素化したいと思います。アイデアは所有することですalias iseRemoveSetup='unalias p1;...;pn'。プログラムエイリアスをより簡単に構成するために、iseRemoveSetupいくつかの機能を定義しました。ただし、iseAddToRemoveCallエイリアスコマンド(ここanalyzer)から呼び出すと効果はありません。シェルから直接呼び出すと正常に動作します。

私に関連する部分は次のとおりです.bashrc

alias iseRemoveSetup=''
function iseAddToRemove() {
  alias iseRemoveSetup=`(alias iseRemoveSetup | cut -f2 -d "'")`"unalias $1;"
}
function iseAddToRemoveCall() {
  iseAddToRemove $1
  echo "iseRemoveSetup;$1"
}

alias setupise='source /home/ted/Xilinx/tools/14.7/ISE_DS/settings64.sh'
alias analyzer='setupise;'`iseAddToRemoveCall "analyzer"`

私は次の機能を持つことがアイデアであることを知っています。

function iseAlias() {
  alias $1='setupise;'`iseAddToRemoveCall $1`
}

しかし、まず上記の問題を解決したいと思います。を実行すると問題が明らかになり、type iseRemoveSetup次のように出力されます。

iseRemoveSetup is aliased to `'

答え1

問題は、エイリアス定義(その1つiseRemoveSetup)がサブシェルにあることです。

エイリアスアナライザ= 'setupise;''iseAddToRemoveCall "アナライザ"

開始されたサブシェルの場合、iseAddToRemoveCall "analyzer"エイリアス定義はそのサブシェルにのみ影響し、この行が完了すると消えます。

この問題は変更すると解決される可能性があります。

alias analyzer='setupise;'`iseAddToRemoveCall "analyzer"`

到着

alias analyzer='setupise;$(iseAddToRemoveCall analyzer)'

echo "iseRemoveSetup;$1"(in iseAddToRemoveCall)をに変更してくださいecho "unalias $1;$1"。したがって、unaliasエイリアス拡張の一部となり、正しいシェルで実行されます。

選ぶ

私にとっては、これらすべてが奇妙に見えます。サブシェルを起動し(Enter bash)、インストーラを実行し、コマンドを実行してから、^D完了したらサブシェルを離れる()は合理的ではありませんか?

追加情報

man 1 bash:

代替テキストの最初の単語はエイリアスがあるかどうかをテストしますが、拡張する単語と同じエイリアスを持つ単語は再び拡張されません。つまり、ls は ls -F にエイリアスを付けることができ、bash は代替テキストを再帰的に拡張しようとしません。

したがって、エイリアスを呼び出す前にunalias p1エイリアスを定義する必要はありませんpi

エイリアスを解放したいコマンドと一緒に(関連付け)配列を使用してから、その配列を使用することをお勧めします。

してはいけないことをするので、これも重要です。

Bash は、その行からコマンドを実行する前に、常に入力の行全体を 1 つ以上読みます。エイリアスは、コマンドの実行時ではなく、コマンドの読み込み時に拡張されます。したがって、他のコマンドと同じ行に表示されるエイリアス定義は、次の入力行を読むまで適用されません。行のエイリアス定義の後に続くコマンドは、新しいエイリアスの影響を受けません。この動作は関数の実行時にも問題になります。関数定義自体が複合コマンドであるため、関数が実行されるのではなく、関数定義を読み取るとエイリアスが拡張されます。したがって、関数で定義されたエイリアスは、関数が実行された後にのみ使用できます。安全のために、常に別名定義を別々の行に配置し、複合コマンドに別名を使用しないでください。

関連情報