bash-completion でコマンド補完を設定する

全般

補完って便利だよね!

はじめに

積みゲーが多すぎていろいろと中途半端になっている Bell です。
今回は cli のシェルを使っているときに利用している Tab キーの補完についてです。
当たり前のように使いつつどう実装されているのか知らなかったので少し調べてみました。

前提条件

久しぶりのコマンドって使い方を忘れてしまいますよね。
想定として普段は自動でリリースされるシステムを何らかの理由で手動で行ったと仮定しましょう。
release コマンドの補完を設定してみます。

やってみよう

まずは release コマンドを作成します。

touch /usr/local/bin/release
chmod 755 /usr/local/bin/release

今回は実行する必要はないので中身は空で OK です。
次に /etc/bash_completion.d/ に補完の設定を保存しましょう。

touch /etc/bash_completion.d/release

内容はひとまずこちら

__release_bash_completion()
{
  echo 
  echo 'update build deploy restart'
}
complete -F __release_bash_completion release

これで設定ファイルを読み込みタブ補完をすると echo のメッセージが確認できるかと思います。

source /etc/bash_completion.d/release
release <Tab> <Tab>

補完で設定された関数が動いてますね、シンプルです。
ですがプロンプトが戻ってきていませんね。 COMPREPLY 変数にメッセージを渡すよう修正しましょう。
ついでにサブコマンドの階層構造も持たせてみましょう。

__release_bash_completion()
{       
    case "$3" in
        release) message="update build deploy restart";;
        build) message="test package";;
    esac
    COMPREPLY=(${message})
}
complete -F __release_bash_completion release

分岐を作ってマッチングしているだけなのでほとんど普通のシェルスクリプトですね。

第三引数には入力し終えた値が入っています。
コマンド名だけの場合にはコマンド名の release を、release update などサブコマンドを入力した場合にはその値が入ってきます。
これを利用して入力されているサブコマンドに応じたメッセージの表示が可能です。
例の場合では update deploy restart が入力されている場合はそのまま表示しますが、
build の場合だけはテストを実行するのかパッケージを作成するのか選べるようなイメージです。

第二引数には入力途中の値が入っています。
前方一致の候補を出力する場合なんかに利用できますね。

これでお手製コマンドにも補完が表示できるわけなのですが、内部で使うだけなら usage をきちんと書いておくほうが効果的だったり・・・?
サブコマンドの階層が深かったり、オプションが多い場合はありがたいかもですね!

ではでは。

コメント