I have JSON that looks like this:
test.json
[
{
"item1": {
"item2": 123,
"array1": [
{
"item3": 456,
"item4": "teststring"
},
{
"item3": 789,
"item4": "teststring2"
}
]
}
}
]
I am trying to print it out in the following format:
123, 456, teststring
123, 789, teststring2
I tried to do it like this:
cat test.json | jq -r '.[].item1.item2, (.[].item1.array1[] | .item3, .item4)' | xargs printf "%s, %s, %s\n"
But the result is that item2
is printed, followed by item3
and item4
in the first line, and then only item3
and item4
are printed in the next line, like so:
123, 456, teststring
789, teststring2,
How can I make the element on the outside of the array print for every set of elements that are printed from within the array?
Doing the processing of the output with shell's printf()
with xargs
is not needed as you can do the processing entirely in jq
itself.
You need to iterate over the values of .item3
and .item4
each time for one unique value of .item2
. To have the result in proper CSV format, format the array using @csv
and for tabular representation you can use @tsv
jq -r '.[].item1 as $data | $data.array1[] | [ $data.item2 , .item3 , .item4 ] | @csv' json
Also it does not make sense to lose quotes around the .item4
values in your expected output, as they are the expected to be retained in a valid JSON string attribute.
If you still need to loose the quotes and represent them as raw strings, you can use join
on the formed array
jq -r '.[].item1 as $data | $data.array1[] | [ ($data.item2|tostring) , (.item3|tostring) , .item4 ]|join(", ")'