CLOVER🍀

That was when it all began.

YAMLに対してjq的な使い方ができるyq(2種類)を試す

これは、なにをしたくて書いたもの?

実は初出のネタではありません。以前、こちらで軽く使ったことがあります。

YAMLで複数行の文字列を入力したい - CLOVER🍀

まあ、今回も軽く済ませるつもりなのですが。

YAMLファイルに対して、jq的なことをやれるコマンドをまとめておこう的なエントリーです。

yqですね。

2つのyq

jqのYAML版ということで、そこからストレートにたどりつく名前であるyqというものがあります。

ただこのyq、2種類あります。

yq documentation

yq

こちらはPythonで書かれたyqで、jqのラッパーです。つまりjqを必要とします。

yq documentation

またYAMLだけではなく、XMLやTOMLもサポートしています。正確には、それぞれxq、tomlqという別コマンドですが。

一方でこちらはGoで書かれたyqで、jqを必要としません。

yq

YAML以外には、JSON、INI、XMLをサポートしています。

Ubuntu Linuxを使っているとaptでインストールできるのですが、こちらはPython版(jqのラッパー)です。

$ apt show yq
Package: yq
Version: 3.1.0-3
Priority: optional
Section: universe/utils
Origin: Ubuntu
Maintainer: Ubuntu Developers <ubuntu-devel-discuss@lists.ubuntu.com>
Original-Maintainer: Debian Python Team <team+python@tracker.debian.org>
Bugs: https://bugs.launchpad.net/ubuntu/+filebug
Installed-Size: 70.7 kB
Depends: jq, python3-argcomplete, python3-toml, python3-xmltodict, python3-yaml, python3:any
Homepage: https://github.com/kislyuk/yq
Download-Size: 16.9 kB
APT-Sources: http://archive.ubuntu.com/ubuntu noble/universe amd64 Packages
Description: Command-line YAML processor - jq wrapper for YAML documents
 yq transcodes YAML documents to JSON and passes them to jq. The
 package also includes xq, which transcodes XML to JSON using
 xmltodict and pipes it to jq, and tomlq, which uses the toml library
 to transcode TOML to JSON, then pipes it to jq

どちらを使っているのか、ちょっと注意しておきましょうね。

今回は両方を軽く試しておきます。

環境

今回の環境はこちら。

$ lsb_release -a
No LSB modules are available.
Distributor ID: Ubuntu
Description:    Ubuntu 24.04.4 LTS
Release:        24.04
Codename:       noble


$ uname -srvmpio
Linux 6.8.0-100-generic #100-Ubuntu SMP PREEMPT_DYNAMIC Tue Jan 13 16:40:06 UTC 2026 x86_64 x86_64 x86_64 GNU/Linux

サンプル

入力にするサンプルとしては、こんなYAMLを用意しました。Go版のyqのドキュメントを少しカスタマイズしたものです。

sample.yaml

root:
  items:
    - name: apple
      type: fruit
    - name: carrot
      type: vegetable
    - name: banana
      type: fruit
  label: sample

Python版yqを使う

まずはPython版yqを使います。

$ sudo apt install yq

バージョン。なんと、0.0.0というすごい表示になります。

$ yq --version
yq 0.0.0

apt showで見た時はこうでしたね。

Version: 3.1.0-3

ヘルプは、jqコマンドにyqの内容を重ねたもののようですね。後ろにjqのヘルプが続くという変わった構造になっています。

$ yq --help
usage: yq [options] <jq filter> [input file...]

yq: Command-line YAML processor - jq wrapper for YAML documents

yq transcodes YAML documents to JSON and passes them to jq.
See https://github.com/kislyuk/yq for more information.

positional arguments:
  jq_filter
  files

options:
  -h, --help            show this help message and exit
  --yaml-output, --yml-output, -y
                        Transcode jq JSON output back into YAML and emit it
  --yaml-roundtrip, --yml-roundtrip, -Y
                        Transcode jq JSON output back into YAML and emit it. Preserve YAML tags and styles by representing them as extra items in their enclosing mappings and sequences while in JSON. This option is incompatible with jq filters that do not expect these extra items.
  --yaml-output-grammar-version {1.1,1.2}, --yml-out-ver {1.1,1.2}
                        When using --yaml-output, specify output grammar (the default is 1.1 and will be changed to 1.2 in a future version). Setting this to 1.2 will cause strings like 'on' and 'no' to be emitted unquoted.
  --width WIDTH, -w WIDTH
                        When using --yaml-output, specify string wrap width
  --indentless-lists, --indentless
                        When using --yaml-output, indent block style lists (sequences) with 0 spaces instead of 2
  --in-place, -i        Edit files in place (no backup - use caution)
  --version             show program's version number and exit

jq - commandline JSON processor [version 1.7]

Usage:  jq [options] <jq filter> [file...]
        jq [options] --args <jq filter> [strings...]
        jq [options] --jsonargs <jq filter> [JSON_TEXTS...]

jq is a tool for processing JSON inputs, applying the given filter to
its JSON text inputs and producing the filter's results as JSON on
standard output.

The simplest filter is ., which copies jq's input to its output
unmodified except for formatting. For more advanced filters see
the jq(1) manpage ("man jq") and/or https://jqlang.github.io/jq/.

Example:

        $ echo '{"foo": 0}' | jq .
        {
          "foo": 0
        }

Command options:
  -n, --null-input          use `null` as the single input value;
  -R, --raw-input           read each line as string instead of JSON;
  -s, --slurp               read all inputs into an array and use it as
                            the single input value;
  -c, --compact-output      compact instead of pretty-printed output;
  -r, --raw-output          output strings without escapes and quotes;
      --raw-output0         implies -r and output NUL after each output;
  -j, --join-output         implies -r and output without newline after
                            each output;
  -a, --ascii-output        output strings by only ASCII characters
                            using escape sequences;
  -S, --sort-keys           sort keys of each object on output;
  -C, --color-output        colorize JSON output;
  -M, --monochrome-output   disable colored output;
      --tab                 use tabs for indentation;
      --indent n            use n spaces for indentation (max 7 spaces);
      --unbuffered          flush output stream after each output;
      --stream              parse the input value in streaming fashion;
      --stream-errors       implies --stream and report parse error as
                            an array;
      --seq                 parse input/output as application/json-seq;
  -f, --from-file file      load filter from the file;
  -L directory              search modules from the directory;
      --arg name value      set $name to the string value;
      --argjson name value  set $name to the JSON value;
      --slurpfile name file set $name to an array of JSON values read
                            from the file;
      --rawfile name file   set $name to string contents of file;
      --args                consume remaining arguments as positional
                            string values;
      --jsonargs            consume remaining arguments as positional
                            JSON values;
  -e, --exit-status         set exit status code based on the output;
  -V, --version             show the version;
  --build-configuration     show jq's build configuration;
  -h, --help                show the help;
  --                        terminates argument processing;

Named arguments are also available as $ARGS.named[], while
positional arguments are available as $ARGS.positional[].

ちなみにyqをインストールすると、xq-pythonコマンドとtomlqコマンドが使えるようになっていたりします。

$ xq-python --version
xq 0.0.0


$ tomlq --version
tomlq 0.0.0

なにも考えずにyqを通すと、なんとJSONになります。

$ cat sample.yaml | yq
{
  "root": {
    "items": [
      {
        "name": "apple",
        "type": "fruit"
      },
      {
        "name": "carrot",
        "type": "vegetable"
      },
      {
        "name": "banana",
        "type": "fruit"
      }
    ],
    "label": "sample"
  }
}

出力をYAMLにするには-yオプションが必要です。今回はこれを付けておきます。

$ cat sample.yaml | yq -y
root:
  items:
    - name: apple
      type: fruit
    - name: carrot
      type: vegetable
    - name: banana
      type: fruit
  label: sample

配列に対して実行。

$ cat sample.yaml | yq -y '.root.items'
- name: apple
  type: fruit
- name: carrot
  type: vegetable
- name: banana
  type: fruit


$ cat sample.yaml | yq -y '.root.items[1]'
name: carrot
type: vegetable

出力がテキストの場合は微妙な出力結果になります。

$ cat sample.yaml | yq -y '.root.items[2].name'
banana
...


$ cat sample.yaml | yq -y '.root.label'
sample
...

この場合は-rオプションを付けましょう。

これは、文字列をエスケープなしで出力するオプションです。

$ cat sample.yaml | yq -r '.root.items[2].name'
banana


$ cat sample.yaml | yq -r '.root.label'
sample

なお、-yとの同時利用はできません。

$ cat sample.yaml | yq -y -r '.root.label'
yq: Error running jq: JSONDecodeError: Expecting value: line 1 column 1 (char 0).

ちなみに、ずっとcatコマンドからパイプでつなげていますが、直接ファイルを指定してもOKです。

$ yq -y '.root.items[2]' sample.yaml
name: banana
type: fruit

Go版yqを使う

続いてGo版のyqを使います。

Ubuntu LinuxだとSnapでインストールできるようですが、今回はGitHubのReleasesからバイナリーをダウンロードします。

$ curl -L https://github.com/mikefarah/yq/releases/download/v4.52.4/yq_linux_amd64 -o $HOME/.local/bin/yq
$ chmod +x $HOME/.local/bin/yq

バージョン。

$ yq --version
yq (https://github.com/mikefarah/yq/) version v4.52.4

ヘルプ。

$ yq --help
yq is a portable command-line data file processor (https://github.com/mikefarah/yq/)
See https://mikefarah.gitbook.io/yq/ for detailed documentation and examples.

Usage:
  yq [flags]
  yq [command]

Examples:

# yq tries to auto-detect the file format based off the extension, and defaults to YAML if it's unknown (or piping through STDIN)
# Use the '-p/--input-format' flag to specify a format type.
cat file.xml | yq -p xml

# read the "stuff" node from "myfile.yml"
yq '.stuff' < myfile.yml

# update myfile.yml in place
yq -i '.stuff = "foo"' myfile.yml

# print contents of sample.json as idiomatic YAML
yq -P -oy sample.json


Available Commands:
  completion  Generate the autocompletion script for the specified shell
  eval        (default) Apply the expression to each document in each yaml file in sequence
  eval-all    Loads _all_ yaml documents of _all_ yaml files and runs expression once
  help        Help about any command

Flags:
  -C, --colors                          force print with colors
      --csv-auto-parse                  parse CSV YAML/JSON values (default true)
      --csv-separator char              CSV Separator character (default ,)
      --debug-node-info                 debug node info
  -e, --exit-status                     set exit status if there are no matches or null or false is returned
      --expression string               forcibly set the expression argument. Useful when yq argument detection thinks your expression is a file.
      --from-file string                Load expression from specified file.
  -f, --front-matter string             (extract|process) first input as yaml front-matter. Extract will pull out the yaml content, process will run the expression against the yaml content, leaving the remaining data intact
      --header-preprocess               Slurp any header comments and separators before processing expression. (default true)
  -h, --help                            help for yq
  -I, --indent int                      sets indent level for output (default 2)
  -i, --inplace                         update the file in place of first file given.
  -p, --input-format string             [auto|a|yaml|y|kyaml|ky|json|j|props|p|csv|c|tsv|t|xml|x|base64|uri|toml|hcl|h|lua|l|ini|i] parse format for input. (default "auto")
      --lua-globals                     output keys as top-level global variables
      --lua-prefix string               prefix (default "return ")
      --lua-suffix string               suffix (default ";\n")
      --lua-unquoted                    output unquoted string keys (e.g. {foo="bar"})
  -M, --no-colors                       force print with no colors
  -N, --no-doc                          Don't print document separators (---)
  -0, --nul-output                      Use NUL char to separate values. If unwrap scalar is also set, fail if unwrapped scalar contains NUL char.
  -n, --null-input                      Don't read input, simply evaluate the expression given. Useful for creating docs from scratch.
  -o, --output-format string            [auto|a|yaml|y|kyaml|ky|json|j|props|p|csv|c|tsv|t|xml|x|base64|uri|toml|hcl|h|shell|s|lua|l|ini|i] output format type. (default "auto")
  -P, --prettyPrint                     pretty print, shorthand for '... style = ""'
      --properties-array-brackets       use [x] in array paths (e.g. for SpringBoot)
      --properties-separator string     separator to use between keys and values (default " = ")
      --security-disable-env-ops        Disable env related operations.
      --security-disable-file-ops       Disable file related operations (e.g. load)
      --shell-key-separator string      separator for shell variable key paths (default "_")
  -s, --split-exp string                print each result (or doc) into a file named (exp). [exp] argument must return a string. You can use $index in the expression as the result counter. The necessary directories will be created.
      --split-exp-file string           Use a file to specify the split-exp expression.
      --string-interpolation            Toggles strings interpolation of \(exp) (default true)
      --tsv-auto-parse                  parse TSV YAML/JSON values (default true)
  -r, --unwrapScalar                    unwrap scalar, print the value with no quotes, colours or comments. Defaults to true for yaml (default true)
  -v, --verbose                         verbose mode
  -V, --version                         Print version information and quit
      --xml-attribute-prefix string     prefix for xml attributes (default "+@")
      --xml-content-name string         name for xml content (if no attribute name is present). (default "+content")
      --xml-directive-name string       name for xml directives (e.g. <!DOCTYPE thing cat>) (default "+directive")
      --xml-keep-namespace              enables keeping namespace after parsing attributes (default true)
      --xml-proc-inst-prefix string     prefix for xml processing instructions (e.g. <?xml version="1"?>) (default "+p_")
      --xml-raw-token                   enables using RawToken method instead Token. Commonly disables namespace translations. See https://pkg.go.dev/encoding/xml#Decoder.RawToken for details. (default true)
      --xml-skip-directives             skip over directives (e.g. <!DOCTYPE thing cat>)
      --xml-skip-proc-inst              skip over process instructions (e.g. <?xml version="1"?>)
      --xml-strict-mode                 enables strict parsing of XML. See https://pkg.go.dev/encoding/xml for more details.
  -c, --yaml-compact-seq-indent         Use compact sequence indentation where '- ' is considered part of the indentation.
      --yaml-fix-merge-anchor-to-spec   Fix merge anchor to match YAML spec. Will default to true in late 2025

Use "yq [command] --help" for more information about a command.

こちらはYAMLを渡すと、素直にYAMLが出力されます。

$ cat sample.yaml | yq
root:
  items:
    - name: apple
      type: fruit
    - name: carrot
      type: vegetable
    - name: banana
      type: fruit
  label: sample

使い方は先ほどのyqとほとんど同じですね。

$ cat sample.yaml | yq '.root.items'
- name: apple
  type: fruit
- name: carrot
  type: vegetable
- name: banana
  type: fruit


$ cat sample.yaml | yq '.root.items[1]'
name: carrot
type: vegetable

テキストもふつうに出力されます。

$ cat sample.yaml | yq '.root.items[1].name'
carrot


$ cat sample.yaml | yq '.root.label'
sample

シェル補完もできます。

$ echo 'source <(yq shell-completion bash)' >> ~/.bashrc

Shell Completion | yq

出力結果を別のフォーマットにもできたりします。

$ cat sample.yaml | yq '.root.items' -o csv
name,type
apple,fruit
carrot,vegetable
banana,fruit

Working with CSV, TSV | yq

Python版に比べると、より高機能な感じですね。

おわりに

YAMLに対してjq的な使い方ができるyqを2種類試してみました。

個人的にはOSのパッケージマネージャーからインストールできる方が好みなので、使うならPython版yqかなというところ
ですが、機能的にはGo版もよさそうなので迷いどころですね。

少なくとも、実際に使うと慣ればどちらを使うかは決めておかないとですね。混在するとよくわからないことになりそうですし。