Home > Software design >  JQ merge WooCommerce REST API responce
JQ merge WooCommerce REST API responce

Time:02-17

Im trying to parse data from woocommerce from linux console. Need to take only shipping info and item names with quantity.

im making curl request to wp-json/wc/v2/orders/ORDER_ID
then jq '{order_id:.id,ship_info:.shipping,items: (.line_items[] | {name , quantity} ) }'
If order contains two items, jq will return two objects
example:

{
  "order_id": 1234,
  "ship_info": {
    "first_name": "Sam",
    "last_name": "Fisher",
    "company": "",
    "address_1": "24 Mega Drive",
    "address_2": "",
    "city": "Eglinton",
    "state": "WA",
    "postcode": "6032",
    "country": "AU",
    "phone": ""
  },
  "items": {
    "name": "Black T-shirt",
    "quantity": 1
  }
}
{
  "order_id": 1234,
  "ship_info": {
    "first_name": "Sam",
    "last_name": "Fisher",
    "company": "",
    "address_1": "24 Mega Drive",
    "address_2": "",
    "city": "Eglinton",
    "state": "WA",
    "postcode": "6032",
    "country": "AU",
    "phone": ""
  },
  "items": {
    "name": "White T-shirt",
    "quantity": 1
  }
}
                                                                                       
                                                                            

I want merge items and use item's name as a key and item's qty as a value. Please advice how to get output like this

{
  "order_id": 1234,
  "ship_info": {
    "first_name": "Sam",
    "last_name": "Fisher",
    "company": "",
    "address_1": "24 Mega Drive",
    "address_2": "",
    "city": "Eglinton",
    "state": "WA",
    "postcode": "6032",
    "country": "AU",
    "phone": ""
  },
  "items": {
    "White T-shirt": "1",
    "Black T-shirt": "1"
  }
}

CodePudding user response:

With your current jq query you are iterating over the items inside a generated object. That's why you receive one object per item. Rather than merging them afterwards, don't separate them in the first place.

If you changed your query from

jq '{
  order_id: .id,
  ship_info: .shipping,
  items: (.line_items[] | {name, quantity})
}'

to just

jq '{
  order_id: .id,
  ship_info: .shipping,
  items: .line_items
}'

you'd probably already see that .line_items is actually an array.

To transform it according to your desired output, change that line to one of the followings. They should all yield the same result.

  items: (.line_items | map({(.name): .quantity}) | add)
  items: (INDEX(.line_items[]; .name) | map_values(.quantity))
  items: (reduce .line_items[] as $i ({}; .[$i.name] = .quantity))
  • Related