2017-04-20 55 views
0

在我的Postgres數據庫我有JSON,看起來與此類似:更新在Postgres的數組的每一個值JSON

{ 
    "myArray": [ 
     { 
      "myValue": 1 
     }, 
     { 
      "myValue": 2 
     }, 
     { 
      "myValue": 3 
     } 
    ] 
} 

現在我要重新命名myValueotherValue。我無法確定陣列的長度!最好我想使用類似set_jsonb的通配符作爲數組索引,但似乎並不支持。那麼最好的解決方案是什麼?

回答

1

你必須分解一個完整的jsonb對象,修改單個元素並構建對象。

自定義功能會有所幫助:

create or replace function jsonb_change_keys_in_array(arr jsonb, old_key text, new_key text) 
returns jsonb language sql as $$ 
    select jsonb_agg(case 
     when value->old_key is null then value 
     else value- old_key || jsonb_build_object(new_key, value->old_key) 
     end) 
    from jsonb_array_elements(arr) 
$$; 

用途:

with my_table (id, data) as (
values(1, 
'{ 
    "myArray": [ 
     { 
      "myValue": 1 
     }, 
     { 
      "myValue": 2 
     }, 
     { 
      "myValue": 3 
     } 
    ] 
}'::jsonb) 
) 

select 
    id, 
    jsonb_build_object(
     'myArray', 
     jsonb_change_keys_in_array(data->'myArray', 'myValue', 'otherValue') 
     ) 
from my_table; 

id |       jsonb_build_object       
----+------------------------------------------------------------------------ 
    1 | {"myArray": [{"otherValue": 1}, {"otherValue": 2}, {"otherValue": 3}]} 
(1 row) 
0

使用JSON功能絕對是最優雅的,但你可以使用字符替換度日。將json(b)作爲文本投射,執行替換,然後將其更改回json(b)。在這個例子中,我包含引號和冒號,以幫助文本替換目標json鍵而不與值衝突。

CREATE TABLE mytable (id INT, data JSONB); 

INSERT INTO mytable VALUES (1, '{"myArray": [{"myValue": 1},{"myValue": 2},{"myValue": 3}]}'); 
INSERT INTO mytable VALUES (2, '{"myArray": [{"myValue": 4},{"myValue": 5},{"myValue": 6}]}'); 

SELECT * FROM mytable; 

UPDATE mytable 
SET data = REPLACE(data :: TEXT, '"myValue":', '"otherValue":') :: JSONB; 

SELECT * FROM mytable; 

http://sqlfiddle.com/#!17/1c28a/9/4