PostgreSQL - 向 JSONB 数组的每个对象添加键

Posted

技术标签:

【中文标题】PostgreSQL - 向 JSONB 数组的每个对象添加键【英文标题】:PostgreSQL - Add key to each objects of an JSONB array 【发布时间】:2020-03-16 11:39:26 【问题描述】:

我的数据库包含一个表,其中有一列具有 jsonb 类型,我想使用 postgreSQL 中的函数/运算符 更新这些数据的一部分。鉴于我们有这个:


  "A":[
    "index":"1",
    "index":"2"
  ],
  "B":[
    "index":"3",
    "index":"4"
  ]

假设我们要向“A”数组中的对象添加一个带有空数组的键,以便:


  "A":[
    "index":"1", "myArray":[],
    "index":"2", "myArray":[]
  ],
  "B":[
    "index":"3",
    "index":"4"
  ]

我该如何继续?

我已经尝试过这种事情但没有成功:

UPDATE myTable SET myColumn = (myColumn::jsonb)->>'A' || '"myArray":[]'

UPDATE myTable SET myColumn = (
  SELECT jsonb_agg(jsonb_set(
    element, 
    array['A'], 
    to_jsonb(((element ->> 'A')::jsonb || '"myArray":[]')::jsonb)
  ))
  FROM jsonb_array_elements(myColumn::jsonb) element
)::json

UPDATE myTable SET myColumn = (
  SELECT jsonb_each((element ->> 'A')::jsonb) || '"myArray":[]'::jsonb
  FROM jsonb_array_elements(myColumn::jsonb) element
)::json

显然,所有这些测试都失败了。我很难理解 postgreSQL 函数的工作原理。

有人可以帮忙吗?

【问题讨论】:

【参考方案1】:

jsonb_array_elementsjsonb_set 的方法是正确的想法,但不知怎的,你以错误的方式嵌套它们:

UPDATE myTable SET myColumn = jsonb_set(myColumn, 'A', (
  SELECT jsonb_agg( element || '"myArray":[]' )
  FROM jsonb_array_elements(myColumn -> 'A') element
));

(online demo)

顺便说一句,如果您的列已经有 jsonb 数据类型,则不需要任何强制转换。

【讨论】:

非常感谢,它有效!但我添加了一些更改,因为事实上,我的专栏是 json :') 所以我将“myColumn”包含在 to_jsonb() 中;) 必须添加WHERE jsonb_array_length(myColumn -> 'A') > 0; @fedor.belov 该查询是在假设每个 json 对象都有一个数组的 A 属性的情况下编写的。如果不是这样,是的,您需要添加条件或创建数组。

以上是关于PostgreSQL - 向 JSONB 数组的每个对象添加键的主要内容,如果未能解决你的问题,请参考以下文章

Postgresql:搜索jsonb对象数组时如何使用动态值?

PostgreSQL 查询 JSONB 字段中的对象数组

Postgresql:如何查询包含某些值的 JSONb 数组

如何在 Postgresql 中对 JSONB 数组中的值求和?

PostgreSQL:仅当元素唯一时才将元素附加到 jsonb 数组

在 postgresql、选项数组或对象中插入 jsonb 数据,有效方式