PostgreSQL 可以在 INSERT 冲突时更新另一行吗?
Can PostgreSQL's update the other row on INSERT conflict?
我有一个 table 记录了给定 a
的最近插入的 b
:
CREATE TABLE IF NOT EXISTS demo (
id serial primary key,
a int not null,
b int not null,
current boolean not null
);
CREATE UNIQUE INDEX ON demo (a, current) WHERE CURRENT = true;
INSERT INTO demo (a, b, current) VALUES (1, 101, true);
我希望能够插入值,当它们发生冲突时,应该更新新行,并且应该更新 先前 冲突的行。
例如我有
select * from demo;
id | a | b | current
----+---+-----+---------
1 | 1 | 101 | t
然后我 运行 像这样:
INSERT INTO demo (a, b, current)
VALUES (1, 102, true)
ON CONFLICT SET «THE OTHER ONE».current = false;
然后我会看到:
select * from demo;
id | a | b | current
----+---+-----+---------
1 | 1 | 101 | f <- changed
2 | 1 | 102 | t
PostgreSQL 中是否有允许这样做的语法?
正如@Adrian 所提议的那样,您可以使用触发器来完成:
CREATE OR REPLACE FUNCTION before_insert ()
RETURNS trigger LANGUAGE plpgsql AS
$$
BEGIN
UPDATE demo
SET current = false
WHERE a = NEW.a ;
RETURN NEW ;
END ;
$$ ;
CREATE TRIGGER before_insert BEFORE INSERT ON demo
FOR EACH ROW EXECUTE FUNCTION before_insert () ;
查看dbfiddle
中的测试结果
PS :约束 one_per
将防止前几行具有相同的 a
值和 current = false
我有一个 table 记录了给定 a
的最近插入的 b
:
CREATE TABLE IF NOT EXISTS demo (
id serial primary key,
a int not null,
b int not null,
current boolean not null
);
CREATE UNIQUE INDEX ON demo (a, current) WHERE CURRENT = true;
INSERT INTO demo (a, b, current) VALUES (1, 101, true);
我希望能够插入值,当它们发生冲突时,应该更新新行,并且应该更新 先前 冲突的行。
例如我有
select * from demo;
id | a | b | current
----+---+-----+---------
1 | 1 | 101 | t
然后我 运行 像这样:
INSERT INTO demo (a, b, current)
VALUES (1, 102, true)
ON CONFLICT SET «THE OTHER ONE».current = false;
然后我会看到:
select * from demo;
id | a | b | current
----+---+-----+---------
1 | 1 | 101 | f <- changed
2 | 1 | 102 | t
PostgreSQL 中是否有允许这样做的语法?
正如@Adrian 所提议的那样,您可以使用触发器来完成:
CREATE OR REPLACE FUNCTION before_insert ()
RETURNS trigger LANGUAGE plpgsql AS
$$
BEGIN
UPDATE demo
SET current = false
WHERE a = NEW.a ;
RETURN NEW ;
END ;
$$ ;
CREATE TRIGGER before_insert BEFORE INSERT ON demo
FOR EACH ROW EXECUTE FUNCTION before_insert () ;
查看dbfiddle
中的测试结果PS :约束 one_per
将防止前几行具有相同的 a
值和 current = false