JSONB列:仅对存储在具有混合JSONB内容的列中的数组的内容进行排序

时间:2018-07-16 14:42:36

标签: postgresql jsonb postgresql-9.5

我有一个带有JSONB列的表,该表存储JSONB数组/字符串(以下示例中的value_r列)。在JSONB列中仅排序JSONB数组内容(存储字符串)的最简单(有效)方法是什么?

我一直在寻找最简单的方法(因为需要查询,还是需要过程?),因为我必须将其应用于更复杂的SQL代码中。

这是测试代码:

CREATE TABLE test_table (
    id integer,
    ordinality bigint,
    key_r text,
    value_r jsonb
);

INSERT INTO test_table VALUES (1, 1, 'carType', '"sedan"');
INSERT INTO test_table VALUES (1, 1, 'equipment', '["AT", "AC"]');
INSERT INTO test_table VALUES (1, 2, 'extra', '["GPS"]');
INSERT INTO test_table VALUES (1, 2, 'carType', '"hatchback"');
INSERT INTO test_table VALUES (2, 1, 'carType', '"sedan"');
INSERT INTO test_table VALUES (2, 1, 'equipment', '["BB", "AA"]');
INSERT INTO test_table VALUES (3, 1, 'carType', '"hatchback"');
INSERT INTO test_table VALUES (3, 1, 'equipment', '["AT"]');

编辑:

预期的结果-因为我要比较两个不同表中的数组,因此我想统一数组的内容,因此'["AT", "AC"]''["AC", "AT"]'变得相同。坦白地说,使用哪种“默认”排序都没有关系:ASC或DESC-我只需要对两个表运行相同的SQL查询/过程,以使其一致且可比。假设这些是预期的结果:

INSERT INTO test_table VALUES (1, 1, 'carType', '"sedan"');
INSERT INTO test_table VALUES (1, 1, 'equipment', '["AC", "AT"]'); -- change here
INSERT INTO test_table VALUES (1, 2, 'extra', '["GPS"]');
INSERT INTO test_table VALUES (1, 2, 'carType', '"hatchback"');
INSERT INTO test_table VALUES (2, 1, 'carType', '"sedan"');
INSERT INTO test_table VALUES (2, 1, 'equipment', '["AA", "BB"]');  -- change here
INSERT INTO test_table VALUES (3, 1, 'carType', '"hatchback"');
INSERT INTO test_table VALUES (3, 1, 'equipment', '["AT"]');

1 个答案:

答案 0 :(得分:0)

使用功能:

create or replace function jsonb_sort_array(jsonb)
returns jsonb language sql immutable as $$
    select jsonb_agg(elem order by elem)
    from jsonb_array_elements($1) elem
$$;

select *, 
    case jsonb_typeof(value_r)
    when 'array' then jsonb_sort_array(value_r)
    else value_r
    end as sorted_value
from test_table;

 id | ordinality |   key_r   |   value_r    | sorted_value 
----+------------+-----------+--------------+--------------
  1 |          1 | carType   | "sedan"      | "sedan"
  1 |          1 | equipment | ["AT", "AC"] | ["AC", "AT"]
  1 |          2 | extra     | ["GPS"]      | ["GPS"]
  1 |          2 | carType   | "hatchback"  | "hatchback"
  2 |          1 | carType   | "sedan"      | "sedan"
  2 |          1 | equipment | ["BB", "AA"] | ["AA", "BB"]
  3 |          1 | carType   | "hatchback"  | "hatchback"
  3 |          1 | equipment | ["AT"]       | ["AT"]
(8 rows)    

DbFiddle.