INSERT [...] ON CONFLICT 可以用于外键违规吗?
Can INSERT [...] ON CONFLICT be used for foreign key violations?
给出
=> select * from referenced;
referenced_id | name
---------------+-------
1 | one
2 | two
3 | three
和
=> select * from entries;
entry_id | referenced_id | name
----------+---------------+------------------
1 | 3 | references three
其中 referenced_id
和 entry_id
是主键。
我想要 entries
的插入语句,如果 entry_id
已经存在或引用的项目不存在,则跳过插入。第一个很容易做到:
INSERT INTO entries
VALUES (1, 2, 'references two')
ON CONFLICT (entry_id) DO NOTHING;
是否也可以在这里检查外键是否存在?
是的,将您的输入行连接到引用的 table,从而删除 FK 列上不匹配的行:
INSERT INTO entries(entry_id, referenced_id, name)
SELECT val.entry_id, val.referenced_id, val.name
FROM (
VALUES (1, 2, 'references two')
-- more?
) val (entry_id, referenced_id, name)
JOIN referenced USING (referenced_id) -- drop rows without matching FK
ON CONFLICT (entry_id) DO NOTHING; -- drop rows with duplicate id
UPSERT 本身 (INSERT ... ON CONFLICT DO NOTHING
) 仅对独特的违规行为做出反应。 The manual:
ON CONFLICT
can be used to specify an alternative action to raising a unique constraint or exclusion constraint violation error. (See ON CONFLICT Clause below.)
由于 VALUES
表达式现在不直接附加到 INSERT
,列类型不是从目标 table 派生的。在使用非基本类型时,您可能需要显式 cast 输入值。参见:
- Casting NULL type when updating multiple rows
给出
=> select * from referenced;
referenced_id | name
---------------+-------
1 | one
2 | two
3 | three
和
=> select * from entries;
entry_id | referenced_id | name
----------+---------------+------------------
1 | 3 | references three
其中 referenced_id
和 entry_id
是主键。
我想要 entries
的插入语句,如果 entry_id
已经存在或引用的项目不存在,则跳过插入。第一个很容易做到:
INSERT INTO entries
VALUES (1, 2, 'references two')
ON CONFLICT (entry_id) DO NOTHING;
是否也可以在这里检查外键是否存在?
是的,将您的输入行连接到引用的 table,从而删除 FK 列上不匹配的行:
INSERT INTO entries(entry_id, referenced_id, name)
SELECT val.entry_id, val.referenced_id, val.name
FROM (
VALUES (1, 2, 'references two')
-- more?
) val (entry_id, referenced_id, name)
JOIN referenced USING (referenced_id) -- drop rows without matching FK
ON CONFLICT (entry_id) DO NOTHING; -- drop rows with duplicate id
UPSERT 本身 (INSERT ... ON CONFLICT DO NOTHING
) 仅对独特的违规行为做出反应。 The manual:
ON CONFLICT
can be used to specify an alternative action to raising a unique constraint or exclusion constraint violation error. (See ON CONFLICT Clause below.)
由于 VALUES
表达式现在不直接附加到 INSERT
,列类型不是从目标 table 派生的。在使用非基本类型时,您可能需要显式 cast 输入值。参见:
- Casting NULL type when updating multiple rows