つばくろぐ @takamii228

知は力なり

jqのyaml版コマンド yq は2種類ある

以前flutterのバージョン切り替えをCI環境で動的にやる記事の中で、yamlの指定したキーを取り出すのに yqコマンドを使っていたのですが、このyqの利用に関してハマったことをメモとして残しておきます。

takamii.hatenablog.com

yqとは

yqとはjqのyaml版でyamlに対してクエリを発行して部分的な文字列を出力するコマンドです。

jqはこちら。

stedolan.github.io

"yq" でググると2つのyqがヒットする

Googleyq を検索すると、なんと全く異なる2種類がヒットします。

https://www.google.com/search?q=yq

Python製のyq

1つ目はpythonベースの yq コマンドです。

github.com

kislyuk.github.io

pypi.org

yq takes YAML input, converts it to JSON, and pipes it to jq:

とあるので、yamljsonに変換して引数のコマンドを処理しているように見えるのでjqでできることは基本できるようです。jqがないと動きません。

$ cat pubspec.yaml
environment:
  sdk: ">=2.1.0 <3.0.0"
  flutter: 1.12.13+hotfix.8
...

$ cat pubspec.yaml | yq -r .environment.flutter
1.12.13+hotfix.8

Go製のyq

もうひとつはGoでかかれたyqです。こちらはjqが入ってなくても動きます。

github.com

mikefarah.gitbook.io

Pythonのypと比べて、diffやマージ等ができるようです。参照のコマンドも微妙に違う。

$ cat pubspec.yaml 
environment:
  sdk: ">=2.1.0 <3.0.0"
  flutter: 1.12.13+hotfix.8
...

$ yq r pubspec.yaml environment.flutter
1.12.13+hotfix.8

brew install yqで入るのはどっち?

brew install yq で入るyqは、Go製のyqです。

$ brew install yq
==> Downloading https://homebrew.bintray.com/bottles/yq-3.2.1.catalina.bottle.tar.gz
==> Downloading from https://akamai.bintray.com/8c/8cbb0eda1f9d8c20342c41979e2cca5440e6215e85c36a3f2
######################################################################## 100.0%
==> Pouring yq-3.2.1.catalina.bottle.tar.gz
🍺  /usr/local/Cellar/yq/3.2.1: 5 files, 5.9MB

Python製のyqを入れるにはpip経由で入れるか、brewpython-yqと指定するようです。

$ brew install python-yq
==> Downloading https://homebrew.bintray.com/bottles/python-yq-2.10.0_1.catalina.bottle.tar.gz
Already downloaded: /Users/takami228/Library/Caches/Homebrew/downloads/4488cbac19c6771a781cfdfe3532dc49d77b45b388fc700a12154ac416867ade--python-yq-2.10.0_1.catalina.bottle.tar.gz
==> Pouring python-yq-2.10.0_1.catalina.bottle.tar.gz
🍺  /usr/local/Cellar/python-yq/2.10.0_1: 99 files, 617.1KB

どっちがいいの?

どちらもそれなりのスターがついていて、利用記事も出てきます。

ドキュメントを読む限りGoのyqのほうがコマンドがリッチそうに見えますが、指定したキーを取り出すだけの用途であればどちらでもよさそうです。

CIやスクリプトに組み込んでチームとして利用していく場合は、どちらのyqコマンドを使うのかをきちんと明記して、統一しておくのが良いでしょう。

※私のチームでは一時期両方のコマンドが混在していて混乱しました。