0

私は Mac (osx sierra) を使用しており、bash の使用方法を学んでいます。いくつかの概念を理解するために、新しいことに挑戦しています。今回は関数とエイリアスを試していました。しかし、私はこの問題に頭を悩ませることができませんでした:

最初に、この関数を .profile にエコーして、新しいエイリアスと関数を .profile ファイルに簡単に挿入できるようにしました。

function editprofile(){
echo "$@" >> ~/.profile
}

この関数は、一部のエイリアスの挿入で非常にうまく機能しました。しかし、Mac をスリープ状態にするスクリプト (以下のスクリプト) のエイリアスを挿入しようとした後、関数が一重引用符と二重引用符のカスケードでいくつかの問題を引き起こすことに気付きました。これは、一重引用符と二重引用符を何層も使用するほとんどのスクリプトに当てはまると思います。

osascript -e 'tell application "Finder" to sleep' && exit

以下のコードは、関数を使用して上記のコードをエイリアスとして .profile に挿入しようとしたものです。

editprofile 'alias _sleep=' "'" 'osascript -e' "'" 'tell application "Finder" to sleep' "'" '&& exit' "'"

問題は、2 番目のスクリプトが .profile ファイルにエコーされるときに、いくつかのエスケープ文字を保持する必要があることです。そうしないと、コードが bash によって正しく解釈されません。これは、これほど多くの引用符の層を持つ他の多くのスクリプトにも当てはまると思うので、回避策があるかどうかを尋ねるべきですが.

PS関連するメモでは、これを入力すると次のようになります。

function editprofile(){echo "$@" >> ~/.profile}

これの代わりに:

function editprofile(){
echo "$@" >> ~/.profile
}

.profile ファイルに追加すると、スクリプトは機能しません。ラインブレイクのせい?

4

1 に答える 1

1

エイリアスではなく、関数があると仮定します。

_sleep() { osascript -e 'tell application "Finder" to sleep' && exit; }

...でテキストを出力できますdeclare -f。したがって:

declare -f _sleep >>~/.profile

...または、既存のeditprofile関数を使用するには:

editprofile "$(declare -f _sleep)"

最も簡単な方法は次のとおりです。ローカルシェルで関数を定義し、シェル自体にそれを発行する作業を行わせ、発行されたコンテンツを引用して、個々の引数にフィールド分割されないようにします(そしてそれらを持っています)グロブとして個別に評価される引数)。


そのルートに行きたくない場合は、利用可能なアプローチがあります。それらはさまざまな程度の不快感です。

printf -v cmd_var '%q ' osascript -e 'tell application "Finder" to sleep' 

...正しく引用された内容を に入れ"$cmd_var"ます。次に、次のことができます。

printf -v sleep_def '_sleep() { %s && exit; }' "$cmd_var"

...これにより、ローカルで実行するために編集したり、 &c に追加したりsleep_devできる関数宣言が得られます。eval.profile

editprofile "$sleep_def"

...そのコンテキストで適切に動作します。

于 2016-11-09T16:29:11.250 に答える