Skip to content

Expression examples

Identity query (.)

The identity query passes the document through with no mutation. It is the default when neither --query nor -f is given.

Input (config.json):

{"x":1,"y":2}
nesdit config.json --query '.'

Stdout:

{"x":1,"y":2}

Useful for normalising a file to nesdit's canonical encoding without changing any values.


Field access and mutation

Set a field

nesdit config.json --query '.x = 99'

Stdout: {"x":99,"y":2}

Update in-place with |=

|= applies an expression to the current value of the field:

nesdit config.json --query '.x |= . + 1'

Stdout: {"x":2,"y":2} (incremented by 1)

Chained mutations

Multiple assignments can be chained with |:

nesdit config.json --query '.x = 10 | .y = 20'

Stdout: {"x":10,"y":20}


Deletion

Delete a key

nesdit config.json --query 'del(.y)'

Stdout: {"x":1}

Delete an array element by index

Input:

{"items":[10,20,30,40,50]}
nesdit data.json --query 'del(.items[2])'

Stdout: {"items":[10,20,40,50]}


Conditionals

Apply a query only when a condition is met:

Input (env.yaml):

env: prod
replicas: 1
nesdit env.yaml --query 'if .env == "prod" then .replicas = 3 else . end'

Stdout:

env: prod
replicas: 3

If .env were "staging", the document would pass through unchanged.


String interpolation

Build a string from a field value using jq's \(.field) syntax:

Input:

{"name":"myapp","version":"1.0"}
nesdit app.json --query '.name = "prefix-\(.name)"'

Stdout:

{"name":"prefix-myapp","version":"1.0"}

--arg: inject a shell variable as a string

--arg K=V binds $K in the query as a literal string. Numbers passed this way remain strings.

Input (a.json):

{}
nesdit a.json --create-missing --arg name=alice --query '.user = $name'

Stdout:

{"user":"alice"}

Numbers stay as strings with --arg:

nesdit a.json --create-missing --arg count=42 --query '.count = $count'

Stdout:

{"count":"42"}

--argjson: inject a shell variable as a typed JSON value

--argjson K=V parses V as JSON and binds it as a typed value. Use this for numbers, booleans, arrays, and objects.

Integer:

nesdit a.json --create-missing --argjson count=42 --query '.count = $count'

Stdout:

{"count":42}

Array:

nesdit a.json --create-missing --argjson nums='[1,2,3]' --query '.items = $nums'

Stdout:

{"items":[1,2,3]}

Object:

nesdit a.json --create-missing --argjson cfg='{"a":1}' --query '.cfg = $cfg'

Stdout:

{"cfg":{"a":1}}

If the value is not valid JSON, nesdit exits 1 with an error:

nesdit a.json --argjson v='not-json' --query '.v = $v'
nesdit: error: arg.decode: --argjson v: expected JSON, got "not-json"

--from-file: load a query from a .jq file

For complex or reusable queries, store them in a file:

q.jq:

.z = 99

Input (a.json):

{"x":1,"y":2}
nesdit a.json --from-file q.jq --create-missing

Stdout:

{"x":1,"y":2,"z":99}

The short form is -f:

nesdit a.json -f q.jq --create-missing

Warning

--query and --from-file are mutually exclusive:

nesdit a.json --query '.' -f q.jq
nesdit: error: flag.conflict: --query and --from-file are mutually exclusive


--where: apply query only to matching documents

In a multi-document stream, --where restricts the query to documents that satisfy a jq predicate. Other documents pass through unchanged.

Input (stream.yaml):

env: prod
version: 1
---
env: staging
version: 1
---
env: prod
version: 1
nesdit --format yaml --where '.env == "prod"' --query '.version = 99' < stream.yaml

Stdout:

---
env: prod
version: 99
---
env: staging
version: 1
---
env: prod
version: 99

Stderr (for the skipped document):

nesdit: warn: -:2: where.skipped: document did not match --where predicate

$${VAR} escape — literal ${VAR} in a query

nesdit never interpolates shell environment variables. If you need the literal string ${FOO} in a value, escape the $ by doubling it:

nesdit a.json --create-missing --query '.x = "$${FOO}"'

Stdout:

{"x":"${FOO}"}

The shell environment variable FOO is never read. $${FOO} is always the literal string ${FOO}.


--create-missing: allow queries to create new keys

By default, assigning to a path that does not exist is an error:

Input:

{"a":1}
nesdit config.json --query '.b.c = 2'
nesdit: error: config.json: query.missing_path: path .b does not exist; use --create-missing to allow path creation

Add --create-missing to let nesdit create intermediate containers:

nesdit config.json --create-missing --query '.b.c = 2'

Stdout:

{"a":1,"b":{"c":2}}