postgresql - 在 JSONB 数组中插入元素 - Postgresql
问题描述
假设我有一张桌子:
SELECT * FROM settings;
| id | name | strategies |
| -- | --- | --- |
| 1 | default | [{name: xyz, enabled: true}, {name: bot2, enabled: true}] |
| 2 | new1 | [{name: bot2, enabled: true}, {name: xyz, enabled: false}] |
我想在{name: bot1, enabled: true}
之前添加一个新对象bot2
。
我正在尝试使用这个已回答问题的解决方案:
WITH bot2_index AS (SELECT
pos- 1 AS bot2_index
FROM
settings,
jsonb_array_elements(strategies) WITH ordinality arr(elem, pos)
WHERE
NAME = 'default'
AND elem->>'name' = 'bot2')
UPDATE settings
SET strategies = jsonb_set(strategies, '{bot2_index}', '{
"name": "bot1",
"enabled": false
}', TRUE);
但我明白了
ERROR: path element at position 1 is not an integer: "bot2_index"
bot2_index
是类型bigint
所以为什么这种语法不起作用?
我还尝试了其他变体,例如bot2_index
, bot2_index::int
, bot2_index::string
,甚至将其作为两个单独的查询运行(如在接受的答案中),但它也不起作用。
编辑#1
这种语法有效,但它似乎替换了该索引处的元素,而不是在给定索引处的元素之前或之后附加元素 - 我怎样才能让它像 JSsplice()
函数一样工作?
UPDATE settings
SET strategies = jsonb_set(strategies, concat('{',(SELECT
pos- 1 AS bot2_index
FROM
settings,
jsonb_array_elements(strategies) WITH ordinality arr(elem, pos)
WHERE
NAME = 'default'
AND elem->>'name' = 'js:bot2'),'}')::text[], '{
"name": "bot1",
"enabled": false
}', TRUE);
解决方案
首先,对于您当前的查询,您应该像下面这样使用它:
WITH bot2_index AS (SELECT
pos- 1 AS bot2_index
FROM
settings,
jsonb_array_elements(strategies) WITH ordinality arr(elem, pos)
WHERE
name = 'default'
AND elem->>'name' = 'bot2')
UPDATE settings
SET strategies = jsonb_set(strategies, array[bot2_index::text], '{
"name": "bot1",
"enabled": false
}'::jsonb, false) from bot2_index;
但是查询会替换现有的一个 DEMO
你应该使用jsonb_insert
它而不是jsonb_set
.
WITH bot2_index AS (SELECT
pos- 1 AS bot2_index
FROM
settings,
jsonb_array_elements(strategies) WITH ordinality arr(elem, pos)
WHERE
name = 'default'
AND elem->>'name' = 'bot2')
UPDATE settings
SET strategies = jsonb_insert(strategies, array[bot2_index::text], '{
"name": "bot1",
"enabled": false
}'::jsonb, false) from bot2_index;
推荐阅读
- mongodb - 为什么猫鼬模式数组中的验证不起作用?
- swift - Swift - “Alamofire.upload” -> “AF.upload” 上传功能的问题
- vagrant - Vagrant-up 无法使用 arrikto/minikf 出现错误
- android - Android Studio Android Emulator Hypervisor Driver... 目录不存在?
- typescript - 如何在此处正确合并
- bioinformatics - Home Questions Tags Users Unanswered 仅提取蛋白质结构数据表面的氨基酸残基
- sql - SQL增量数据
- angular - Ionic 4.1.1 中的“ToastOptions”类型中不存在“标题”和“按钮”,这与文档相反
- java - 上传多个文件在spring boot控制器中不起作用
- python - 如何从xpath中的当前节点遍历到父节点?