How to Verify Keys in JSON Using jq
Quick techniques to validate keys in JSON with no iteration
Context
A peer seek my inputs on parsing JSON. The requirements are:
To determine whether a key exists or available without
jq
throwing errorThe queries are to be executed in a pipeline
Overview
I set out to explore the different ways of parsing JSON with jq
using its built-in operators and functions.
You can try it along on your local machine or via the
jq
online playground.The query and
jq
Command line (CLI) command will be provided along with the explanation below.I will be mainly parsing the nested objects.
I will be using the following sample JSON file (generated by our friend ChatGPT) to test out the different approaches, saved into a file named sample.json
.
{
"id": 12345,
"name": "RandomUser",
"isActive": true,
"age": 29,
"address": {
"street": "123 Random St",
"city": "Randomville",
"state": "RA",
"zipcode": "12345"
},
"preferences": {
"notifications": {
"email": true,
"sms": false
},
"theme": "dark"
},
"accountStatus": "Active",
"createdAt": "2023-01-01T12:00:00Z",
"updatedAt": "2024-08-31T14:30:00Z",
"metadata": {
"lastLogin": "2024-08-31T14:00:00Z",
"subscription": {
"plan": "Premium",
"renewalDate": "2025-01-01"
}
}
}
empty
and alternative operator
A method I learned from one of my projects is using the alternative operator ('//') and empty
keyword.
It is useful when the subsequent operation(s) expects an input.
By standardizing to return no result instead of the "null" string, you can leverage on comparison operators such as
-z
for empty or-n
for non-empty value in shell-script.
You can try the following queries to observe the differences between the usage of empty
and alternative operator.
Without //empty
Note that without empty
, the output returned when a invalid or non-existent path is provided is a string value of null
.
jq Query | jq Command Line | Expected output |
.preferences.notifications.email | jq '.preferences.notifications.email' sample.json | true |
.preferences.email | jq '.preferences.email' sample.json | null |
With //empty
Upon using //empty
, for invalid or non-existent path, no results will be returned.
jq Query | jq Command Line | Expected output |
.preferences.notifications.email//empty | jq '.preferences.notifications.email//empty' sample.json | true |
.preferences.email//empty | jq '.preferences.email//empty' sample.json | <No output> |
has()
function
Referencing to a Stack Overflow Post, the has()
function may be what we are looking for to explicitly determine if a given key exists
This may be more intuitive, to check if the key exists
Will return
true
orfalse
Do note that it is not transitive, so you need to navigate to the target attribute before using the
has()
function
jq Query | jq Command Line | Expected output | ||
.preferences | has("notifications") | jq '.preferences | has("notifications")' sample.json | true |
. | has("notifications") | jq '. | has("notifications")' sample.json | false |
Conclusion
Depending on the context of your workflow, there's probably more than 1 way to determine in verifying the keys in a JSON.
For now, just noting it down here to share with my peer and hope this may be useful to you too!
Cheers!