【问题标题】:Wildcard when Traversing JSONB Array in Postgres在 Postgres 中遍历 JSONB 数组时的通配符
【发布时间】:2017-11-17 16:20:19
【问题描述】:

我们目前正在试用 JSONB 作为我们正在构建的系统中的订单数据的数据类型。由于文档相当大,这里是它的第一部分(重要的部分):

{
"appMessage": {
    "order": {
        "customerSurname": "Tyreus",
        "shipment": {
            "asnNumber": "CC56477332",
            "shippingStore": "3321"
        },
        "orderNumber": "7991218655",
        "propositionCollectionStoreNumber": "5656",
        "collectionPointId": "4",
        "customerFirstname": "Isaac",
        "orderLine": [{
            "collectionWindowFrom": "2017-01-18T09:00:00+00:00",
            "lineNo": "1",
            "skuNo": "7654321",
            "createdDateTime": "2017-01-17T17:54:31+00:00",

我们面临的问题是在将通配符应用于数组中的某些内容时。使用上面的示例,我将如何进行通配符搜索以说出“检索所有 skuNo 以 7 开头的记录”?

在数组之外我测试了通配符,例如:

SELECT 
    * 
FROM 
    ORDERS 
WHERE 
    ORDER_DATA->'appMessage'->'message'->>'enterpriseCode' LIKE 'TU%';

成功了。但是一旦数组进入方程,一切就变得不清楚了......

任何帮助将不胜感激。

【问题讨论】:

    标签: arrays json postgresql jsonb


    【解决方案1】:

    您可以使用 jsonb_array_elements 取消嵌套 JSONB 数组,然后对其进行过滤:

    --Using 'intermediary' table unnested_json_array
    WITH test_data(json_column) AS (
    
        SELECT 
            jsonb_build_array(
                jsonb_build_object('lineNo', '1', 'skuNo', '7654321'), 
                jsonb_build_object('lineNo', '2', 'skuNo', '1654321'),
                jsonb_build_object('lineNo', '3', 'skuNo', '7654321')           
            )
    
    ), unnested_json_array(json_column) AS (    
        SELECT jsonb_array_elements((SELECT * FROM test_data))
    ) 
    SELECT * FROM unnested_json_array WHERE json_column->>'skuNo' ILIKE '7%';
    
    --Or even simpler using LATERAL JOIN   
    WITH test_data(json_column) AS (
        SELECT 
            jsonb_build_array(
                jsonb_build_object('lineNo', '1', 'skuNo', '7654321'), 
                jsonb_build_object('lineNo', '2', 'skuNo', '1654321'),
                jsonb_build_object('lineNo', '3', 'skuNo', '7654321')           
            )
    ) 
    SELECT 
        json_elements.* 
    FROM 
        test_data 
        JOIN LATERAL jsonb_array_elements(test_data.json_column) AS json_elements (order_line) ON TRUE 
    WHERE 
        order_line->>'skuNo' ILIKE '7%';
    
    --In your case:
    SELECT 
        json_elements.* 
    FROM 
        ORDERS 
        JOIN LATERAL jsonb_array_elements(ORDER_DATA->'appMessage'->'order'->'orderLine') AS json_elements (order_line) ON TRUE 
    WHERE 
        order_line->>'skuNo' LIKE '7%';
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-08-10
      • 2019-03-21
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多