web-dev-qa-db-ja.com

PostgreSql:json配列データをフラット化

私の現在のクエリから、次のjsonbデータを取得します。

values: "a1", ["b1", "b2"]

そして、私はこれを次のように1つのレベルのみで平坦化したいと思います。

values: "a1", "b1", "b2"

クエリでデータを取得する簡単な方法を次に示します(可能なのは2レベルのみで、それ以上はできません)。

SELECT * 
FROM jsonb_array_elements('{"test": ["a1", ["b1", "b2"]]}'::jsonb->'test');

私はjsonb_array_elementsを使用しようとしましたが、私の問題は次のとおりです。それがjson配列であるかどうかわかりません! SQLの専門家ではないので、次のようなコードを書く方法は見つかりませんでした。

SELECT
    IF (is_json_array(list)) 
        jsonb_array_elements(list)
    ELSE
        list
    ENDIF
FROM jsonb_array_elements('{"test": ["a1", ["b1", "b2"]]}'::jsonb->'test');

私の現在のデータの「ズームアウト」ビューについては、ここにテーブルなしの動作テストがあります:

with recursive search_key_recursive (jsonlevel) as(
    values ('{"fr": {"WantedKey": "a1", "Sub": [{"WantedKey": ["b1", "b2"]}], "AnotherSub": [{"WantedKey": "c1"}]}}'::jsonb)
    union all
    select 
        case jsonb_typeof(jsonlevel)           
            when 'object' then (jsonb_each(jsonlevel)).value        
            when 'array' then jsonb_array_elements(jsonlevel)   
        end as jsonlevel
    from search_key_recursive where jsonb_typeof(jsonlevel) in ('object', 'array')
)
select search_key_recursive.jsonlevel->'WantedKey'
from search_key_recursive
where jsonlevel ? 'WantedKey';

後で、結果をinsertステートメントで使用します。

INSERT INTO table1 
SELECT 'someText', value 
FROM jsonb_array_elements('{"test": ["a1", "b1", "c1"]}'::jsonb->'test');
3
vibby

とった !

SELECT 
case jsonb_typeof(json)
    when 'string' then json->>0
    when 'array' then jsonb_array_elements_text(json)
end
FROM jsonb_array_elements('{"test": ["a1", ["b1", "b2"]]}'::jsonb->'test') as json;
4
vibby