zsh - スクリプトがオプション設定を読み取れないのはなぜですか?

zsh - スクリプトがオプション設定を読み取れないのはなぜですか?

zsh 5.8.1(x86_64-apple-darwin21.0)を使用すると、次に依存します。zsh デフォルトの配列インデックスは 1 から始まります。、以前のユーザー設定がこれを妨げないことを確認したいと思います。最善の方法は、ユーザーの現在のKSH_ARRAYS設定を保存してからこのオプションをオフにしてから、完了したらオプションを元の設定にリセットすることです。私は以下を持っています:

#!/usr/bin/env zsh

if [[ -o ksharrays ]]; then
  echo "setting ksharrays_is_set to 1...";
  ksharrays_is_set=1;
else
  echo "setting ksharrays_is_set to 0...";
  ksharrays_is_set=0;
fi

unsetopt KSH_ARRAYS;

# here is where my script runs

if [[ ksharrays_is_set -eq 1 ]]; then
  echo "setting the ksharrays option...";
  setopt ksharrays;
fi

これをテストするためにsetopt ksharrays端末で実行し、スクリプトを実行しました。ただし、setting ksharrays_is_set to 0...端末ではまだエコーが表示されます。

setopt ksharrays2行目(shebangの直下)に追加すると、予想されるsetting ksharrays_is_set to 1...内容が表示されます。setting the ksharrays option...

端末で設定するとオプションが選択されず、スクリプトで設定すると選択されるのはなぜですか?

編集:また、このファイルを追加してsetopt ksharraysingし、~/.zshrc上記のスクリプトを実行してみました。これは予想される出力とは異なる結果をもたらしました。引数なしで端末でコマンドを実行して、コマンドが適用されることを確認しました。~/.zshenvsourcesetting ksharrays_is_set to 0...setopt

$ setopt

combiningchars
interactive
ksharrays
login
monitor
promptsubst
shinstdin
zle

echo $(setopt)編集2:スクリプトの上部に追加しました。印刷される唯一のことは、nohashdirs引数なしで端末で直接実行しても他のオプションが表示されないことcombiningcharsですinteractivesetopt

答え1

別のプログラムでプログラムを実行すると、各プログラムはそれ自体になります。 zshでzshを実行しても、2番目のzshが何らかの方法で親からいくつかの設定を継承するわけではありません。

zshスクリプトを作成しました。したがって、を実行すると、/path/to/your/scriptオペレーティングシステムはファイルが次に終了することを発見します。シェルボーン行を入力し、zshコマンド検索パスで実行します。誰がプロセスを開始したかは問題ではありません。 zshの新しいインスタンスはデフォルト設定で始まります。設定に対するすべての変更(zshオプションなど)は、コマンドライン、設定ファイル、スクリプトの内容などの場所で行う必要があります。

一部の設定は、あるプログラムが別のプログラムを呼び出すときに継承されますが、これはzshだけでなくすべてのプログラムに適用される設定です。主に、環境変数遺伝的です。 Zsh は環境変数に基づいてオプションを設定しません。

使用する場合.またはsource内蔵zshから。これは.、コマンドを含むファイルに書き込まれたかのように、ファイルからコマンドを読み取るようにzshに指示します。残念ながら、これら2つの状況を区別できる明確な用語はありません。どちらも「スクリプト」と呼ばれます。スクリプトは実行(/path/to/scriptすべてのプログラムで実行)またはソースとして提供(. /path/to/scriptzshで実行)できます。同じファイルをどちらの方向でも使用できますが、ほとんどのスクリプトは一方向にのみ使用できます。あなたのスクリプトは実行されるスタンドアロンプ​​ログラムです。

zshが実行スクリプトの実行を開始したときに何が起こるかを見てみましょう。 zshがスクリプトを実行してもロードされませんが.zshrc(zsh対話型ランタイムのみ)ロードされます。/etc/zshenvそして~/.zshenv。と入力すると、setopt ksh_arraysスクリプトはその設定を受け入れます。どのsetoptコマンド(またはほぼすべてのコマンド)を入力するのは悪い.zshenv考えであり、スクリプトは中断されます。

スクリプトが終了すると、誰もどのzshオプションを有効にしたか気にしません。したがって、ksh_arraysスクリプト内のすべてのコードを有効にするには、setopt ksh_arraysストーリーの終わりであるスクリプトの先頭で実行するだけです。

コードの一部にのみ特定のオプションが必要な場合は、その部分を関数に入れて設定します。local_options機能のオプション。たとえば、ksh_arrays関数の実行時に有効にし、終了時にデフォルト設定を復元するには、setopt local_options ksh_array関数の上部近くに配置します。また、一部のオプションを変更する必要があるコードは、他のオプションのデフォルト値が変更されると中断されることがよくあります。したがって、オプションがデフォルト値から変更された可能性があるコンテキストでzshコードを実行する必要がある場合は、そのコードを関数に入れて実行します。emulate -LR zshその機能から。これにより、機能がデフォルトのオプションとして実行およびlocal_options有効になり、機能が終了するとオプションの変更がキャンセルされます。一部のコードは特定の「エンドユーザー」オプションに従う必要があります。たとえば、mark_dirsこれらのコードではemulate -L zsh(例:削除-R)オプションを使用します。たとえば、完成関数の場合も同様です。

関連情報