如何在 Postgres 中更新 2 列之一的冲突?

Posted

技术标签:

【中文标题】如何在 Postgres 中更新 2 列之一的冲突?【英文标题】:How to upsert in Postgres on conflict on one of 2 columns? 【发布时间】:2016-05-04 02:01:11 【问题描述】:

当表中的两列之一发生冲突时,是否可以在 Postgres 9.5 中执行 upsert。基本上我有 2 列,如果任一列抛出唯一约束违规,那么我想执行更新操作。

【问题讨论】:

【参考方案1】:

我认为在 Postgres 9.5 ON CONFLICT 中只能有一个约束或多个列名,但多个列必须有一个索引

【讨论】:

【参考方案2】:

是的,这是默认行为。如果指定了ON CONFLICT DO UPDATE,则任何唯一约束违规都会构成冲突,然后执行UPDATEINSERT 语句只能有一个ON CONFLICT 子句,但该子句的conflict_target 可以指定多个列名,每个列名都必须有一个索引,例如UNIQUE 约束。但是,您仅限于单个conflict_action,并且在处理该操作时您将无法获得有关哪个约束导致冲突的信息。如果您需要那种信息,或者根据约束违反的具体操作,您应该编写一个触发函数,但这样您就失去了INSERT ... ON CONFLICT DO ... 语句的最重要的原子性。

【讨论】:

我不确定这是否 100% 正确,诚然问题含糊不清。如果 2 列具有不同的唯一约束(我从问题中理解),那么 ON CONFLICT 只能用于 DO NOTHING。您似乎无法链接或“分离”所谓的冲突目标。 @Jeff 扩展了我的答案。 感谢您的更新。它回答了我自己的问题,即我们是否可以使用相同的 INSERT 处理两种不同的违规行为。

以上是关于如何在 Postgres 中更新 2 列之一的冲突?的主要内容,如果未能解决你的问题,请参考以下文章

如何在 Postgres 9.4 中对 JSONB 类型的列执行更新操作

如何在 typeorm、postgres 中组合 3 列唯一的?

postgres:更新冲突插入行并返回旧值

Spring Data / Hibernate 使用 Postgres 保存实体,在冲突更新某些字段时使用插入

如何选择引用同一列作为外键的所有(表,列)

冲突部分索引的 Postgres 唯一或排除约束无法更新票证