加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 百科 > 正文

如何确定upsert是否是PostgreSQL 9.5 UPSERT的更新?

发布时间:2020-12-13 16:25:34 所属栏目:百科 来源:网络整理
导读:可写CTE被认为是9.5000之前的UPSERT解决方案,如 Insert,on duplicate update in PostgreSQL?所述 可以使用以下信息执行UPSERT:它是否作为UPDATE或INSERT结束,具有以下可写CTE成语: WITH update_cte AS ( UPDATE t SET v = $1 WHERE id = $2 RETURNING 'upd
可写CTE被认为是9.5000之前的UPSERT解决方案,如 Insert,on duplicate update in PostgreSQL?所述

可以使用以下信息执行UPSERT:它是否作为UPDATE或INSERT结束,具有以下可写CTE成语:

WITH
    update_cte AS (
        UPDATE t SET v = $1 WHERE id = $2 RETURNING 'updated'::text status
    ),insert_cte AS (
        INSERT INTO t(id,v) SELECT $2,$1 WHERE NOT EXISTS
            (SELECT 1 FROM update_cte) RETURNING 'inserted'::text status
    )
 (SELECT status FROM update_cte) UNION (SELECT status FROM insert_cte)

该查询将返回“更新”或“插入”,否则可能(很少)会按照https://dba.stackexchange.com/questions/78510/why-is-cte-open-to-lost-updates所述的约束违规操作失败

可以使用PostgreSQL 9.5新的“UPSERT”语法实现类似的功能,从优化中获益,并避免可能的约束违规?

从 @lad2025’s answer年起,结果可以通过将 settings和 customized options与 related functions在WHERE子句中滥用来获得所需的副作用.
CREATE TABLE t(id INT PRIMARY KEY,v TEXT);

INSERT INTO t (id,v)
    SELECT $1,$2
    WHERE 'inserted' = set_config('upsert.action','inserted',true)
    ON CONFLICT (id) DO UPDATE
        SET v = EXCLUDED.v
        WHERE 'updated' = set_config('upsert.action','updated',true)
RETURNING current_setting('upsert.action') AS "upsert.action";

set_config的第三个参数是is_local:true表示在事务结束时设置将消失.更确切地说,current_setting(‘upsert.action’)将返回NULL(而不是抛出一个错误)直到会话结束.

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读