Skip to content

Instantly share code, notes, and snippets.

@yonchu
Last active December 20, 2015 07:29
Show Gist options
  • Save yonchu/6094089 to your computer and use it in GitHub Desktop.
Save yonchu/6094089 to your computer and use it in GitHub Desktop.
解説用 grunt 補完
#compdef grunt
### 変数や関数を使用する場合の注意
# - 変数を使用する場合は、定義が グローバル に漏れないよう、必ず local or typeset(declare) コマンド使って変数宣言を行うこと
# - 関数はグローバルに定義されるため、重複しないよう名前付けには十分配慮すること
# − 短い補完関数であれば、関数を使わずに書くと良い
function __grunt() {
### 必要な変数を定義
# 現在のコンテキスト(curcontext) を保存
# コンテキストは、現在補完しようとしているコマンドを示しています
# 補完によっては _arguments -C などを使用してコンテキストを変更することがあるので、
# 補完関数の先頭で現在のコンテキストを保存しておくのが習慣のようになっています
# なお今回の補完ではコンテキストの変更は行いません
# また、以下の様な値が設定されます
# :complete:grunt:
local curcontext="$curcontext"
# 現在の cache-policy を保存する変数
local update_policy
# 補完対象を保存する変数
local state
# 補完情報を格納する配列
local -a args
# キャッシュが更新されたときのメッセージ
# 無くても良いが、あった方が分かりやすい
local update_msg
### local は1文で書くこともできる
# local curcontext="$curcontext" update_policy state update_msg
# local -a args
### 補完情報を定義
# 詳しい説明は省略
args=(
### オプションの補完
'(- 1 *)'{-h,--help}'[Display this help text]' \
'(--version,-V)'{--version,-V}'[Print the grunt version. Combine with --verbose for more info.]' \
'(--verbose,-v)'{--verbose,-v}'[Verbose mode. A lot more information output.]' \
'(--completion)--completion[Output shell auto-completion rules. See the grunt-cli documentation for more information.]' \
### オプション以外の補完
# オプション以外を補完する時、state 変数に 文字列 'tasks' が設定されます
# tasks という名前は好きな名前を設定できます
# *:->, *::->, *:::-> などの書き方がありますが、詳しい説明は省略
'*: :->tasks' \
)
###############################
# 1.cache-policy を設定
###############################
zstyle -s ":completion:${curcontext}:" cache-policy update_policy
if [[ -z $update_policy ]]; then
zstyle ":completion:${curcontext}:" cache-policy __grunt_caching_policy
fi
### 補完
# オプションの補完なら、オプションが補完され return
# タスクの補完なら state 変数に 'tasks' が設定され処理継続
_arguments $args && return
########################################
# 2.キャッシュの復元と更新を行う
########################################
###
# グローバル変数 __grunt_tasks にタスク情報が設定される
if __grunt_retrieve_update_cache; then
update_msg='(cache updated)'
fi
### タスクの補完かどうか判別
case $state in
tasks)
######################
# 3.タスク補完
######################
# __grunt_tasks 変数と _describe 関数を使用してタスクを補完
_describe "grunt task$update_msg" __grunt_tasks || return 1
;;
esac
return
}
############################################################
# 4.キャッシュの復元と必要ならキャッシュの更新を行う
############################################################
# キャッシュファイル名: grunt
# キャッシュ変数名: __grunt_tasks
function __grunt_retrieve_update_cache() {
if ( ! (( $+__grunt_tasks )) \
|| _cache_invalid 'grunt' ) \
&& ! _retrieve_cache 'grunt'; then
### キャッシュの更新が必要
# 新たに grunt のタスク情報を取得
__grunt_tasks=(${(f)"$(__grunt_get_tasks)"})
### キャッシュを保存
_store_cache 'grunt' __grunt_tasks
return 0
fi
return 1
}
### grunt のタスク情報を取得
# 実装はダミーです
function __grunt_get_tasks() {
local tasks
### grunt --help を実行
tasks=$(grunt --help)
### タスク情報を加工して以下の形式に変換
# 形式:
# タスク名:タスクの説明
# 例:
# clean:Clean files and folders
tasks=( \
"hoge:hoge task" \
"fuga:fuga task" \
"clean:Clean files and folders" \
)
# 配列を改行で連結して出力
echo "${(j:\n:)tasks}"
}
#######################################
# 5.cache-policy に設定する関数
#######################################
# $1 にキャッシュファイルのパスが入っています
#
# 戻り値:
# 真 (return 0) : キャッシュ無効
# 偽 (return 非ゼロ) : キャッシュ有効
function __grunt_caching_policy() {
local -a oldp
# Nm+7 と指定するとキャッシュの有効期限が 7日 となる
# Nmw+1 と指定すると 1週間
# Nmh+1 と指定すると 1時間
# Nmm+1 と指定すると 1分
oldp=( "$1"(Nm+7) )
(( $#oldp ))
}
__grunt "$@"
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment