Jas*_*Lee 4 postgresql indexing json unique-index postgresql-9.4
我现在正在测试 Postgresql 9.4 beta2。我想知道是否可以在嵌入式 json 对象上创建唯一索引?
我创建了一个表名products:
CREATE TABLE products (oid serial primary key, data jsonb)
Run Code Online (Sandbox Code Playgroud)
现在,我尝试将 json 对象插入到数据列中。
{
"id": "12345",
"bags": [
{
"sku": "abc123",
"price": 0,
},
{
"sku": "abc123",
"price": 0,
}
]
}
Run Code Online (Sandbox Code Playgroud)
但是,我希望sku包包独一无二。这意味着 json 不能插入到 products 表中,因为sku在这种情况下它不是唯一的。
我试图创建一个像下面这样的唯一索引,但它失败了。
CREATE UNIQUE INDEX product_sku_index ON products( (data->'bags'->'sku') )
Run Code Online (Sandbox Code Playgroud)
有什么建议?
UNIQUE INDEX由于多种原因,您在表达式上创建 a 的尝试注定会失败。
CREATE UNIQUE INDEX product_sku_index ON products( (data->'bags'->'sku') )
第一个也是最平凡的幸福是...
不不参考任何东西。你可以引用数组的第一个元素
data->'bags'->'sku'
data->'bags'->0->>'sku'
Run Code Online (Sandbox Code Playgroud)
或更短:
data#>>'{bags,0,sku}'
Run Code Online (Sandbox Code Playgroud)
但该表达式只返回数组的第一个值。
您的定义:“我希望包的 sku 是独一无二的” .. 不清楚。您希望 的值sku是唯一的吗?在一个 JSON 对象中还是在列中的所有 json 对象中data?或者您想将数组限制为带有sku?
无论哪种方式,这些目标都不能通过简单的UNIQUE索引来实现。
如果您希望sku 值在 中的所有 json 数组中都是唯一的data->'bags',有一种方法。取消嵌套数组并将所有单个sku值写入具有唯一(或 PK)约束的简单辅助表中的单独行:
CREATE TABLE prod_sku(sku text PRIMARY KEY); -- PK enforces uniqueness
Run Code Online (Sandbox Code Playgroud)
此表可用于其他目的。
下面是一个与普通 Postgres 数组非常相似的问题的完整代码示例:
仅适应取消嵌套技术。代替:
DELETE FROM hostname h
USING unnest(OLD.hostnames) d(x)
WHERE h.hostname = d.x;
...
INSERT INTO hostname(hostname)
SELECT h
FROM unnest(NEW.hostnames) h;
Run Code Online (Sandbox Code Playgroud)
用:
DELETE FROM prod_sku p
USING jsonb_array_elements(NEW.data->'bags') d(x)
WHERE p.sku = d.x->>'sku';
...
INSERT INTO prod_sku(sku)
SELECT b->>'sku'
FROM jsonb_array_elements(NEW.data->'bags') b
Run Code Online (Sandbox Code Playgroud)
详情是:
| 归档时间: |
|
| 查看次数: |
2616 次 |
| 最近记录: |