vpas
vpas

Reputation: 533

jq merge multiple keys into one object

I would like to make (using jq) from input:

{
 key1: value1,
 key2: value2,
 key3: [
  {key4: value3, key5: value5},
  {key4: value4, key5: value6},
  .
  .
  .
  {key4: valueN, key5: valueM},
  .
  .
  .
 ]
}

this output:

{
  key1: value1,
  key2: value2,
  value3: value5,
  value4: value6,
  .
  .
  .
  valueN: valueM,
  .
  .
  .
}

How to do it?

I have tried some ways, but I haven't able to find the proper solution, mainly jq generated separated objects, I would like to have only one output object containing keys from input object.

Upvotes: 0

Views: 918

Answers (3)

pmf
pmf

Reputation: 36131

I would use a reduce on .key3's items and append them successively:

reduce .key3[] as {$key4, $key5} (del(.key3); .[$key4] = $key5)
{
  "key1": "value1",
  "key2": "value2",
  "value3": "value5",
  "value4": "value6",
  "valueN": "valueM"
}

Demo

Upvotes: 2

Thor
Thor

Reputation: 47099

key3 almost has the format that from_entries uses, tweak it?

.key3                 |
map(.key   = .key4)   |
map(.value = .key5)   |
map( del(.key4,.key5) )

Converts key3 array to:

[
  {
    "key": "value3",
    "value": "value5"
  },
  {
    "key": "value4",
    "value": "value6"
  },
  {
    "key": "valueN",
    "value": "valueM"
  }
]

Pipe to from_entries:

( ... | from_entries) as $obj | . + $obj | del(.key3)

Output:

{
  "key1": "value1",
  "key2": "value2",
  "value3": "value5",
  "value4": "value6",
  "valueN": "valueM"
}

Upvotes: 0

Inian
Inian

Reputation: 85600

For the given input, the following should produce the desired output

.key3 as $t | del(.key3) | . + ( $t | map(to_entries | { (.[0].value) : .[1].value } ) | add ) 

jq-play link

Upvotes: 2

Related Questions