从CSV执行COPY时自动生成ID列

时间:2016-02-02 18:45:12

标签: postgresql csv

我有一个简单的表(4个文本列和一个ID列)。我正在尝试导入没有ID列的CSV文件。

在Postico中我有这样的架构设置: enter image description here

DROP TABLE changes;
CREATE TABLE changes(
id    SERIAL PRIMARY KEY,
commit_id TEXT,
additions INTEGER,
deletions INTEGER,
file_id TEXT
);
CREATE TEMP TABLE tmp_x AS SELECT * FROM changes LIMIT 0;
COPY tmp_x(commit_id,additions,deletions,file_id) FROM '/Users/George/git-parser/change_file' (format csv, delimiter E'\t');
INSERT INTO changes SELECT * FROM tmp_x
ON CONFLICT DO NOTHING;
DROP TABLE tmp_x;

但我收到错误ERROR: null value in column "id" violates not-null constraint

1 个答案:

答案 0 :(得分:3)

您需要指定列:

COPY tmp_x (commit_id, additions, deletions, file_id) 
FROM '/Users/George/git-parser/change_file' (format csv, delimiter E'\t');

copy语句中指定的列顺序显然必须与输入文件中列的顺序匹配。

您还需要更改insert声明。

INSERT INTO changes SELECT * FROM tmp_x

会将tmp_x中的所有列插入目标表,但由于您未在id中将serial列定义为tmp_x } table,没有生成任何内容并插入了null个值。并且您的insert语句只复制那些空值。

您需要跳过id声明中的insert列:

INSERT INTO changes (commit_id,additions,deletions,file_id) 
SELECT commit_id,additions,deletions,file_id
FROM tmp_x
ON CONFLICT DO NOTHING;

您实际上可以从id

中删除tmp_x