おそらくはそれさえも平凡な日々

JSONを使ってコマンドラインを動的に組み立てて実行するjfillを作った

https://github.com/Songmu/jfill

標準入力からJSONを受け取り、その値を使ってコマンドラインを組み立てて実行するユーティリティです。以下のような具合です。

インストール

% go get github.com/Songmu/jfill/cmd/jfill

もしくはGitHub Releasesからご利用ください。

使い方

% echo '{"name":"jfill"}' | jfill echo Hello {{name}}!
Hello jfill!

{{name}} の部分がプレースホルダーです。それがJSONの入力を元に置換され実行されています。

プレースホルダー内には以下のようにデフォルト値を指定することも可能です。

% echo '{}' | jfill echo Hello {{name:jfill}}!
Hello jfill!

{{name:jfill}} のコロン以降の"jfill"の部分がデフォルト値です。プレースホルダーにデフォルト値が指定されておらず、置換対象のキーがJSON内に存在しない場合、jfillは失敗します。

深い構造のJSONに対応するために、プレースホルダー内にXPathのような文字列を指定することができます。内部的には github.com/mattn/go-scan を利用しています。

% echo '{"Songmu":{"age":38}}' | jfill echo Songmu is {{/Songmu/age}} years old.
Songmu is 38 years old.

作った動機

主にMackerelのチェック監視で、引数を動的に指定させる仕組みが欲しかったのが動機。何らかのパラメーターストアとjfillと連携させれば動的に引数を指定できます。以下はmackerel-agent.confのサンプル。

[plugin.checks.unicorn-worker]
command = '''
  echo '{"threshold":'$(getconf _NPROCESSORS_ONLN)'}' \
  | jfill check-procs -P unicorn --critical-under={{threshold:5}}
'''

少しわざとらしい例ですが、この場合、CPUコア数よりもワーカー数が少なくなった時にアラートが上がります。JSONが正しく出力できなかったときにエラーになるのを防ぐためにデフォルト値を指定するのが推奨です。

ConsulのKVSやMackerelのmetadata APIと組み合わせるのも賢い方法です。ちなみにMackerelのmetadata APIを利用する際に毎分アクセスするのは効率が悪いため、何らかのキャッシュ機構を使うことを強く推奨します。(お願いします…!

環境変数を動的にセットしたい場合

env コマンドと組み合わせると良いでしょう。

% echo '{"lang":"ja_JP.UTF-8"}' | jfill env LANG={{lang}} date
2018年 6月12日 火曜日 01時27分28秒 JST

fillinとの違い

https://github.com/itchyny/fillin というものがありまして、僕も便利に使っているのですが、ユースケースが違うため、別で作ることにしました。

まとめ

ぜひご利用ください!仕組み上、結構危ないことができてしまうため、ご利用は計画的に!

あわせて読みたい

created at
last modified at

2018-06-12T01:29:01+0900

comments powered by Disqus