以下が必要なカスタムスクリプトがあります。
- 短い/長い形式のオプションパラメータ
- 必須コマンドライン引数
次の短い/長いコマンドラインオプション:
-r, --readonly
-m, --mount
必須パラメーターの場合、パラメーターは実際にはスクリプト内のCaseステートメントとして指定されます。つまり、この例foo
では次のようになります。bar
case $1 in
foo )
:
;;
bar )
:
;;
zsh completion
次のパラメータが開始されたときにオプションのパラメータが完了するようにスクリプトを生成し、スクリプトケースの説明から必須パラメータを-
取得するにはどうすればよいですか。
修正する:
答えからインスピレーションを受け、これまでに得た内容は次のとおりです@Marlon Richert
。
myscript.sh
私のカスタムスクリプトが呼び出され、私が作成した完了ルールが次の場所にあるとしましょう/usr/share/zsh/functions/Completion/Unix/_myscript.sh
。
#compdef myscript.sh
_myscript () {
local -a args
args+=(
{-r,--readonly}'[description for "readonly"]'
{-m,--mount}'[description for "mount"]'
)
_arguments $args && return
}
_myscript "$@"
私のスクリプトmyscript.sh
自体は/usr/local/bin/myscript.sh
。
オプションのパラメータがあり、それを処理するときに、-r
スクリプトに必要なコマンドラインパラメータに対してCaseステートメントのエントリが完全に提供されるように、完了ルールを変更する必要が-m
あります。/usr/local/bin/myscript.sh
args+=(
また、スクリプトの6行目で始まるブロックを完成する構文が正しいかどうかわかりません。一重引用符はどこに入れるべきですか?
答え1
完成を定義したい関数が呼び出されたとしますmyfunc
。
まず、実際の機能を設定してみましょう。
myfunc
.notesというファイルに関数を配置します。.zsh
これはまたはで終わりません.sh
。- 関数を独自のファイルに配置するときに定型句を追加する必要はありません
funcname() {…}
。
- ファイルが含まれているディレクトリが
myfunc
あることを確認してください$fpath
。たとえば、ファイルがmyfunc
ある場合は、ファイル~/Functions
に以下を追加します~/.zshrc
。fpath+=( ~/Functions )
- 最後に
myfunc
ファイルに自動ロードします~/.zshrc
。# We pass a couple of options that make the code # less likely to break: # -U suppresses alias expansion # -z marks the function for zsh-style autoloading == # `unsetopt KSH_AUTOLOAD` autoload -Uz myfunc
myfunc
これで、コマンドラインで使用できます(まだ何も実行されていません)。
次に、完成関数を作成しましょう。
- というファイルを作成します
_myfunc
。 - このファイルを入れてください:
#compdef myfunc # The line above means "This function generates # completions for myfunc." # The combination of that line, plus the file name # starting with an `_`, plus having this file's # parent dir in your `$fpath`, ensures this file # will be autoloaded when you call `compinit`. # `+X` makes sure `myfunc`'s definition will get # loaded immediately, even if you have not called # this function yet. autoload +X -Uz myfunc # Get the definition of `myfunc` in string form. local funcdef="$( type -f myfunc )" # Get the part that matches `case*esac`, then split # it on whitespace and put the resulting words in an # array. local -a words=( ${=funcdef[(r)case,(r)esac]} ) # Keep only the words that start with `(` and end # with `)`. # Even if you used the `case` syntax with only the # closing `)`s, `type -f` will show your cases with # both `(` and `)`. local -a required=( ${(M)words:#'('*')'} ) # `-s`: Allow options to `myfunc ` to be stacked, # that is, you are allowed to specify `myfunc -rm`. # If not, remove the `-s` option. # `*:`: Let this argument be completed in any # position. _arguments -s \ {-r,--readonly}'[description for "readonly"]' \ {-m,--mount}'[description for "mount"]' \ "*:required argument:( ${required//[()]/} )"
required argument
呼び出すパラメータに置き換えます。- オプションの説明を入力します。
- もう一度、ファイルがあるディレクトリが
$fpath
。 - これを
autoload -Uz compinit; compinit
実行して実行されていることを確認してください。.zshrc
後ろに上記のディレクトリがに追加されました$fpath
。 - シェルを再起動する
exec zsh
か、ターミナルウィンドウを閉じて新しいウィンドウを開きます。
これで完了できますmyfunc
。
readonly
が相互に排他的である場合は、mount
次のように完成関数の最後の行を再構築する必要があります。
_arguments \
(-m --mount){-r,--readonly}'[description for "readonly"]' \
(-r --readonly){-m,--mount}'[description for "mount"]' \
"*:required argument:( ${required//[()]/} )"