2

Is it possible to pass and use in jq a variable of type array?

jq --arg ips "${IPs[0]}" '.nodes.app.ip = $ips[0] | .nodes.data.ip = $ips[1]' nodes.json
ybonda
  • 1,546
  • 25
  • 38

1 Answers1

3

The general case solution is to pass that array in on stdin with NUL delimiters:

IPs=( 1.2.3.4 5.6.7.8 )
original_doc='{"nodes": { "app": {}, "data": {} }}'

jq -Rn --argjson original_doc "$original_doc" '
  input | split("\u0000") as $ips
  | $original_doc
  | .nodes.app.ip = $ips[0]
  | .nodes.data.ip = $ips[1]
' < <(printf '%s\0' "${IPs[@]}")

...emits as output:

{
  "nodes": {
    "app": {
      "ip": "1.2.3.4"
    },
    "data": {
      "ip": "5.6.7.8"
    }
  }
}

This is overkill for an array of IP addresses, but it works in the general case, even for actively-hostile arrays (ones with literal quotes, literal newlines, and other data that's intentionally hard-to-parse).


If you want to keep stdin clean, you can use a second copy of jq to convert your array to JSON:

IPs=( 1.2.3.4 5.6.7.8 )
IPs_json=$(jq -Rns 'input | split("\u0000")' < <(printf '%s\0' "${IPs[@]}"))

jq --argjson ips "$IPs_json" '
    .nodes.app.ip = $ips[0]
  | .nodes.data.ip = $ips[1]
' <<<'{"nodes": { "app": {}, "data": {} }}'
Charles Duffy
  • 280,126
  • 43
  • 390
  • 441
  • Its working locally, but when I'm sending it via ssh jq doesn't work properly... https://stackoverflow.com/questions/58428131/sending-jq-with-argjson-via-ssh – ybonda Oct 17 '19 at 11:38