Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

jq parse string array and string object

I have this json string:

json_string="{\"emailRecipients\":\"['test@example.com', 'tes2t@example.com', 'test3@example.com']\", \"anotherEmails\":\"{'test1': 'test1@example.com', 'test2': 'test2@example.com', 'test3': 'test3@example.com'}\", \"some_key\": 3, \"another_key\": \"some_value\"}"

I’m trying to use jq to parse the emailRecipients as a json array and anotherEmails as a json object.

I’m trying to make a command that can work with any key, not emailRecipients just and anotherEmails. I also need to keep keys-values that don’t have json objects/arrays inside intact.

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

So I tried to do this:

parsed_json=$(echo "$json_string" | jq 'with_entries(
    .value |= if startswith("\"[") and endswith("\"]") then
        gsub("''";"\"") | fromjson
    else
        .
    end
)')

But I don’t know why the gsub isn’t working. Any idea of what I’m doing wrong ?

>Solution :

You seem to be confusing syntax with values. The quotes are not part of the value; the value starts and ends with [ and ], respectively (not "[ and "]; the latter doesn’t even make sense if the syntax quote was part of the value). To detect objects, you need to check for { and } prefix and suffix. You need to filter for string values, otherwise you cannot apply the startswith filter.

Full program:

map_values(
    if type == "string" and (startswith("[") and endswith("]") or startswith("{") and endswith("}")) then
        gsub("'"; "\"") | fromjson
    else
        .
    end
)

When used in a shell context:

parsed_json=$(printf '%s\n' "$json_string" | jq 'map_values(
    if type == "string" and (startswith("[") and endswith("]") or startswith("{") and endswith("}")) then
        gsub("'\''"; "\"") | fromjson
    else
        .
    end
)')

or

parsed_json=$(printf '%s\n' "$json_string" | jq "map_values(
    if type == \"string\" and (startswith(\"[\") and endswith(\"]\") or startswith(\"{\") and endswith(\"}\")) then
        gsub(\"'\"; \"\\\"\") | fromjson
    else
        .
    end
)")
Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading