我有这样的story_id
表。
Column | Type | Modifiers
--------------+---------+-------------------------------------------------------------------
id | integer | not null default nextval('story_sites_id_seq'::regclass)
story_id | integer | not null
site_id | integer | not null
我想添加site_id = 12
和story_id
的新行已经有site_id = 70
,这是我的查询,它运作良好:
INSERT INTO story_sites (story_id, site_id)
SELECT story_id, 12
FROM story_sites
WHERE site_id = 70;
但如果有行已经有site_id = 12
,我将得到一个重复键错误。
所以我想排除那些重复的行,这是我的新查询,但它不能正常工作,它在我认为应该没有插入任何内容。似乎我也不能在Postgres 9.4中使用ON CONFLICT DO NOTHING
。我该怎么办?
INSERT INTO story_sites (story_id, site_id)
SELECT story_id, 12
FROM story_sites
WHERE site_id = 70
AND NOT EXISTS
(
SELECT id
FROM story_sites
WHERE site_id = 12
);
你很亲密你只需要考虑story_id
:
INSERT INTO story_sites (story_id, site_id)
SELECT ss.story_id, 12
FROM story_sites ss
WHERE ss.site_id = 70 AND
NOT EXISTS (SELECT id
FROM story_sites ss2
WHERE ss2.site_id = 12 AND ss2.sotry_id = ss.story_id
);
总而言之,如果同时发生多个插入,此查询仍有可能出现问题。你真正应该使用的是on conflict do nothing
,documentation为insert
解释。
从版本9.4升级到9.5不要进行子请求。它可能导致性能下降。从Postgres 9.5开始,你可以简单地使用:
INSERT INTO my_table (id, name) VALUES (1, 'Me')
ON CONFLICT DO NOTHING;