如何更新 jsonb 的 PostgreSQL 数组
How to update PostgreSQL array of jsonb
我有一个 table 喜欢:
id: integer,
... other stuff...,
comments: array of jsonb
评论栏的结构如下:
[{
"uid": "comment_1",
"message": "level 1 - comment 1",
"comments": [{
"uid": "subcomment_1",
"message": "level 2 - comment 1",
"comments": []
}, {
"uid": "subcomment_2",
"message": "level 1 - comment 2",
"comments": []
}]
},
{
"uid": "P7D1hbRq4",
"message": "level 1 - comment 2",
"comments": []
}
]
我需要更新特定字段,例如:comments[1](with uid = comment_1) -> comments[2] (with uid = subcomment_2) -> message = 'comment edited'
.
我是 postgre 的新手sql,我不知道如何做到这一点,甚至没有关闭。我设法合并对象并更改级别 1 的消息:
UPDATE tasks
set comments[1] = comments[1]::jsonb || $$
{
"message": "something",
}$$::jsonb
where id = 20;
但我只能到此为止了。
有正确方向的提示吗?
乐:
我做到了这一点:
UPDATE tasks
set comments[1] = jsonb_set(comments[1], '{comments,1, message}', '"test_new"')
where id = 20;
当然,我可以从 javascript 获取此路径,但这是最佳做法吗?使用 javascript 数组中的索引感觉不舒服 table。
我应该尝试编写一个 sql 函数来获取数组并使用 'uid' 作为键吗?使用 'uid' ?
的任何其他更简单的 search/select 方法
LLE
我无法使用以下建议使其工作:(我阅读并尝试过)
代码如下 returns 无:
-- get index for level 2
select pos as elem_index
from tasks,
jsonb_array_elements(comments[0]->'comments') with ordinality arr(elem, pos)
where tasks.id = 20 and
elem ->>'uid'='subcomment_1';
而且我需要在多个级别使用它,所以它不是完全重复的。
首先,您不能更新列的一部分(数组的元素),而只能更新整个列。
接下来,你应该明白路径(jsonb_set()
函数的第二个参数)是什么意思了。
最后,函数的第三个参数是有效的json,所以一个简单的文本值必须用单引号和双引号括起来。
update tasks
set comments = jsonb_set(comments, '{0, comments, 1, message}', '"comment edited"')
where id = 1;
路径:
- 0 - 外部数组的第一个元素(元素索引自
0)
- 评论 - 具有键
comments
的对象
- 1 - 第二个元素
comments
数组
- message - 上面的一个对象
message
元素.
我有一个 table 喜欢:
id: integer,
... other stuff...,
comments: array of jsonb
评论栏的结构如下:
[{
"uid": "comment_1",
"message": "level 1 - comment 1",
"comments": [{
"uid": "subcomment_1",
"message": "level 2 - comment 1",
"comments": []
}, {
"uid": "subcomment_2",
"message": "level 1 - comment 2",
"comments": []
}]
},
{
"uid": "P7D1hbRq4",
"message": "level 1 - comment 2",
"comments": []
}
]
我需要更新特定字段,例如:comments[1](with uid = comment_1) -> comments[2] (with uid = subcomment_2) -> message = 'comment edited'
.
我是 postgre 的新手sql,我不知道如何做到这一点,甚至没有关闭。我设法合并对象并更改级别 1 的消息:
UPDATE tasks
set comments[1] = comments[1]::jsonb || $$
{
"message": "something",
}$$::jsonb
where id = 20;
但我只能到此为止了。
有正确方向的提示吗?
乐: 我做到了这一点:
UPDATE tasks
set comments[1] = jsonb_set(comments[1], '{comments,1, message}', '"test_new"')
where id = 20;
当然,我可以从 javascript 获取此路径,但这是最佳做法吗?使用 javascript 数组中的索引感觉不舒服 table。 我应该尝试编写一个 sql 函数来获取数组并使用 'uid' 作为键吗?使用 'uid' ?
的任何其他更简单的 search/select 方法LLE
我无法使用以下建议使其工作:
-- get index for level 2
select pos as elem_index
from tasks,
jsonb_array_elements(comments[0]->'comments') with ordinality arr(elem, pos)
where tasks.id = 20 and
elem ->>'uid'='subcomment_1';
而且我需要在多个级别使用它,所以它不是完全重复的。
首先,您不能更新列的一部分(数组的元素),而只能更新整个列。
接下来,你应该明白路径(jsonb_set()
函数的第二个参数)是什么意思了。
最后,函数的第三个参数是有效的json,所以一个简单的文本值必须用单引号和双引号括起来。
update tasks
set comments = jsonb_set(comments, '{0, comments, 1, message}', '"comment edited"')
where id = 1;
路径:
- 0 - 外部数组的第一个元素(元素索引自 0)
- 评论 - 具有键
comments
的对象
- 1 - 第二个元素
comments
数组 - message - 上面的一个对象
message
元素.