Inspired by a nice tutorial on Baeldung I’ve decided to write done some usual suspects when working with jq. Hence, this is more like a cheatsheet than a regular post.
For practitioners and interactive learners I also recommend the great jq-play online editor where you can try jq directly in the browser.
For our examples below let’s go with the followin' JSON-input (fetched from a micro-profile /health
-endpoint).
{
"outcome": "UP",
"checks": [
{
"name": "core-isAlive",
"state": "UP",
"data": {
"buildtime": "2020-01-29T12:46:05.183Z",
"version": "0.0.1-SNAPSHOT",
"api-versions": "2"
}
},
{
"name": "core-db2-isAlive",
"state": "UP",
"data": {}
},
{
"name": "core-postgres-isAlive",
"state": "UP",
"data": {}
}]
}
In the subsequent examples I use jq
for brevity reasons with a static file-input: jq '.' file.json
But normally I’d use it rather by piping a response directly into it: curl -s http://localhost:8080/health | jq '.'
Queries and their results
Extracting a property(-value) - here the checks
-property:
> jq '.checks' file.json
> jq '.checks[] | .name' file.json
"core-isAlive"
"core-db2-isAlive"
"core-postgres-isAlive"
raw
-output (-r
):> jq -r '.checks[1] | .name' file.json
core-db2-isAlive
> jq '.checks | lengh' file.json
3
> jq '.checks[0].name | length' file.json
12
-c
for compact output):> jq '.checks[0] | keys' file.json -c
["data","name","state"]
> jq '.checks | keys' file.json -c
[0,1,2]
==
, >=
, <
etc.) or regex (using the test
-built-in filter):> jq '.checks[] | select(.state == "UP") | select (.name|test("post"))' file.json
{
"name": "core-postgres-isAlive",
"state": "UP",
"data": {}
}
> jq '.checks[] | select(.data."api-versions"=="2")' file.json
{
"name": "core-isAlive",
"state": "UP",
"data": {
"buildtime": "2020-01-29T12:46:05.183Z",
"version": "0.0.1-SNAPSHOT",
"api-versions": "2"
}
}
2:3
(first inclusive, second exclusive) - you can also omit one of the indices i.e. :3
:> jq '.checks[2:3]' file.json
# outermost brakets form a new array - inner curlies create new objects
> jq '[.checks[] | { service: .name, status: .state }]' file.json
[
{
"service": "core-isAlive",
"status": "UP"
},
{
"service": "core-db2-isAlive",
"status": "UP"
},
{
"service": "core-postgres-isAlive",
"status": "UP"
}
]
> jq '.checks[1] | { (.name): .state }' file.json -c
{"core-db2-isAlive":"UP"}
+
you can combine arrays, strings, numbers and even objects:> jq '.checks[1] | { (.name): .state } + { "plus": (.state +"__"+ .name) }' file.json
{
"core-db2-isAlive": "UP",
"plus": "UP__core-db2-isAlive"
}
join
is useful for preparing scripting-input (also -c
is handy here):> jq '[.checks[] | .name ] | join(" ")' -c file.json
core-isAlive core-db2-isAlive core-postgres-isAlive
add
in case you’d like to sum things up - to convert types use tonumber
or tostring
etc.:> jq '[.checks[] | .data?."api-versions" | select(. != null) | tonumber ] | add' -c file.json
2
split
in combination with first
and last
are handy when extracting things from property-values itself:> # we'd like to extract only the second part of buildtime '2020-01-29T12:46:05.183Z'
> jq '.checks[].data.buildtime | select(. != null) | split("T") | last' file.json
12:46:05.183Z