Postgresql

更新動態 jsonb 對像數組

  • June 24, 2020

我正在嘗試使用新值更新 jsonb 鍵,但我無法一次更新所有鍵。

我的 json 結構是這樣的:

[{
   "type": "button",
   "content": {
       "align": "leftAlign"
   }
}, {
   "type": "button",
   "content": {
       "align": "leftAlign"
   }
}, {
   "type": "button",
   "content": {
       "align": "leftAlign"

   }
}] 

我想align用新值更新鍵,但現在我的查詢並沒有更新所有元素,它只更新一個元素

到目前為止,這是我的查詢:

with align_position as (
   select 
   ('{' || index-1 || ',content,align}' )::text[] as path,
   id
   from section, jsonb_array_elements(entities) with ordinality arr(entity, index)
   where entity->'content'->>'align' = 'leftAlign'
)
update myTable set entities = jsonb_set(entities, align_position.path, '"left"', false) from align_position where section.id = align_position.id;

如何進行查詢以更新所有元素?

有什麼想法嗎?

我設法使用此查詢解決了這個問題:

update
  myTable 
set
  entities = 
  (
     select
        to_jsonb(array_agg (new_values)) 
     from
        (
           select
(
              case
                 when
                    arr -> 'content' ->> 'align' = 'leftAlign' 
                 then
                    jsonb( COALESCE( jsonb_set(arr, '{content}', jsonb(arr ->> 'content') - 'align' || jsonb('{"align": "left"}'), true), '{}' ) ) 
                 when
                    arr -> 'content' ->> 'align' = 'rightAlign' 
                 then
                    jsonb( COALESCE( jsonb_set(arr, '{content}', jsonb(arr ->> 'content') - 'align' || jsonb('{"align": "right"}'), true), '{}' ) ) 
                 when
                    arr -> 'content' ->> 'align' = 'centerAlign' 
                 then
                    jsonb( COALESCE( jsonb_set(arr, '{content}', jsonb(arr ->> 'content') - 'align' || jsonb('{"align": "center"}'), true), '{}' ) ) 
                 else
                    arr 
              end
) as new_values 
           from
              jsonb_array_elements( entities ) as arr 
              group by
                 arr -> 'content' ->> 'align',
                 arr 
        )
        as new_values 
  )
;

引用自:https://dba.stackexchange.com/questions/269169