0

I have a table (log_table) and in this table there is a nested array json field (activities). With using this activities field, I want to normalize my row.

log_table:

- id:long
- activities:json
- date:timestamp

example activities field:

[ 
   { 
      "actionType":"NOTIFICATION",
      "items":null
   },
   { 
      "actionType":"MUTATION",
      "items":[ 
         { 
            "id":387015007,
            "name":"epic",
            "value":{ 
               "currency":"USD",
               "amount":1.76
            }
         },
         { 
            "id":386521039,
            "name":"test",
            "value":{ 
               "currency":"USD",
               "amount":1.76
            }
         }
      ]
   }
]

As query, I've tried:

select 
* 
from 
log_table l, 
json_array_elements(l.activities) elems,
json_array_elements(elems->'items') obj;

With this query, I got error like below:

ERROR:  cannot call json_array_elements on a scalar

Is there any suggestion?

1 Answer 1

1

The lack of items should be marked as [null], not null. You can use the case expression to correct this, e.g.:

select elems->>'actionType' as action_type, obj
from log_table
cross join jsonb_array_elements(l.activities::jsonb) elems
cross join jsonb_array_elements(case elems->'items' when 'null' then '[null]' else elems->'items' end) obj

 action_type  |                                       obj
--------------+---------------------------------------------------------------------------------
 NOTIFICATION | null
 MUTATION     | {"id": 387015007, "name": "epic", "value": {"amount": 1.76, "currency": "USD"}}
 MUTATION     | {"id": 386521039, "name": "test", "value": {"amount": 1.76, "currency": "USD"}}
(3 rows)    
Sign up to request clarification or add additional context in comments.

2 Comments

Thanks for your answer; I also wonder something about it. How can I create index for log->activities->actionTypes->id in here.
There is no type of index that you could use here.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.