PostgreSQL UPSERT(可写CTE)中的模糊列使用一个表来更新另一个表

时间:2013-02-14 19:19:44

标签: postgresql recursive-query upsert

我有一个名为users_import的表,我正在解析并导入CSV文件。如果用户已经存在,我想使用该表我想更新我的users表,如果它不存在则我想要INSERT。 (这实际上是一个非常简单的例子,说明了我正在尝试做的更为复杂的事情。)

我正在尝试做一些与此类似的事情: https://stackoverflow.com/a/8702291/912717

以下是表定义和查询:

CREATE TABLE users (
    id INTEGER NOT NULL UNIQUE PRIMARY KEY,
    name TEXT NOT NULL
);

CREATE TABLE users_import (
    id INTEGER NOT NULL UNIQUE PRIMARY KEY,
    name TEXT NOT NULL
);

WITH upsert AS (
    UPDATE users AS u
    SET
        name = i.name
    FROM users_import AS i
    WHERE u.id = i.id
    RETURNING *
)
INSERT INTO users (name)
    SELECT id, name 
    FROM users_import
    WHERE NOT EXISTS (SELECT 1 FROM upsert WHERE upsert.id = users_import.id);

该查询出现此错误:

psql:test.sql:23: ERROR:  column reference "id" is ambiguous
LINE 11:  WHERE NOT EXISTS (SELECT 1 FROM upsert WHERE upsert.id = us...
                                                       ^

为什么id含糊不清,造成什么?

1 个答案:

答案 0 :(得分:4)

RETURNING *子句中的WITH upsert...包含users中的所有列以及来自联接表users_import的所有列。因此,结果有两列名为id,两列名为name,因此在引用upsert.id时存在歧义。

为避免这种情况,如果您不需要其余列,请使用RETURNING u.id