具有多列唯一约束名称的 PostgreSQL ON CONFLICT
PostgreSQL ON CONFLICT with multi-column unique constraint name
当我尝试使用 PostgreSQL 进行 UPSERT
时,我 运行 陷入了一种我无法理解的行为。文档似乎表明 INSERT
语句的 冲突目标 可以是索引表达式 或 约束名称。但是,在尝试引用约束名称时,出现 "column ... does not exist" 错误。
我的第一次尝试是创建一个 UNIQUE
索引,它与约束推断一起工作得很好:
create table kv (key text, value text, extra text);
create unique index kv_key_value on kv(key, value);
insert into kv (key, value) values ('k1', 'v1');
-- this works:
insert into kv (key, value, extra) values ('k1', 'v1', 'e1')
on conflict (key, value) do update set extra=excluded.extra;
-- this does not
insert into kv (key, value, extra) values ('k1', 'v1', 'e1')
on conflict (kv_key_value) do update set extra=excluded.extra;
描述以上 table,我在 "Indexes:"
下看到以下内容
"kv_key_value" UNIQUE, btree (key, value)
我的第二次尝试是将唯一约束明确地放在创建 table:
create table kv (
key text,
value text,
extra text,
constraint kv_key_value unique(key, value));
描述上述 table,"Indexes:" 的输出略有不同("UNIQUE CONSTRAINT" 与前面示例中的 "UNIQUE"):
"kv_key_value" UNIQUE CONSTRAINT, btree (key, value)
但是我仍然无法将约束名称指定为冲突目标:
insert into kv (key, value, extra) values ('k1', 'v1', 'e1')
on conflict (kv_key_value) do update set extra=excluded.extra;
ERROR: column "kv_key_value" does not exist
LINE 2: on conflict (kv_key_value) do update set extra=exclude...
我是不是误会了什么?我完全明白我可以使用等效表达式并依赖约束推理,但我想知道为什么约束名称在文档听起来应该如此时似乎不起作用?
你的语法有误。
对于约束,应该是:
INSERT INTO kv (key, value, extra)
VALUES ('k1', 'v1', 'e1')
ON CONFLICT ON CONSTRAINT kv_key_value
DO UPDATE SET extra = excluded.extra;
当我尝试使用 PostgreSQL 进行 UPSERT
时,我 运行 陷入了一种我无法理解的行为。文档似乎表明 INSERT
语句的 冲突目标 可以是索引表达式 或 约束名称。但是,在尝试引用约束名称时,出现 "column ... does not exist" 错误。
我的第一次尝试是创建一个 UNIQUE
索引,它与约束推断一起工作得很好:
create table kv (key text, value text, extra text);
create unique index kv_key_value on kv(key, value);
insert into kv (key, value) values ('k1', 'v1');
-- this works:
insert into kv (key, value, extra) values ('k1', 'v1', 'e1')
on conflict (key, value) do update set extra=excluded.extra;
-- this does not
insert into kv (key, value, extra) values ('k1', 'v1', 'e1')
on conflict (kv_key_value) do update set extra=excluded.extra;
描述以上 table,我在 "Indexes:"
下看到以下内容"kv_key_value" UNIQUE, btree (key, value)
我的第二次尝试是将唯一约束明确地放在创建 table:
create table kv (
key text,
value text,
extra text,
constraint kv_key_value unique(key, value));
描述上述 table,"Indexes:" 的输出略有不同("UNIQUE CONSTRAINT" 与前面示例中的 "UNIQUE"):
"kv_key_value" UNIQUE CONSTRAINT, btree (key, value)
但是我仍然无法将约束名称指定为冲突目标:
insert into kv (key, value, extra) values ('k1', 'v1', 'e1')
on conflict (kv_key_value) do update set extra=excluded.extra;
ERROR: column "kv_key_value" does not exist
LINE 2: on conflict (kv_key_value) do update set extra=exclude...
我是不是误会了什么?我完全明白我可以使用等效表达式并依赖约束推理,但我想知道为什么约束名称在文档听起来应该如此时似乎不起作用?
你的语法有误。
对于约束,应该是:
INSERT INTO kv (key, value, extra)
VALUES ('k1', 'v1', 'e1')
ON CONFLICT ON CONSTRAINT kv_key_value
DO UPDATE SET extra = excluded.extra;