sql - "INSERT INTO t(x) .. SELECT MAX(t.x) + 1 .." sometimes returns "DUPLICATE KEY"
问题描述
Good evening,
I've a problem with a simple "INSERT" sql satement that i was assuming that it's "bomb safe" but sometimes i face the error "duplicate key".
Well, i'll give you a simple sql code
-- instruction 1: table create
CREATE TABLE tab_1 (
code integer,
field_1 integer,
PRIMARY KEY (code)
) WITHOUT OIDS;
-- instruction2: the insert
INSERT INTO tab_1 (code)
SELECT
(SELECT COALESCE(MAX(code), 0) + 1 FROM tab_1
)
;
Well, the problem i'm facing is that "sometimes" without any (IMHO) reason, the instruction 2 returns "duplicate key" on the insert for the field "code". Obviously happens randomly, and I cannot explain "why" it happens or "how" i can reproduce the problem at my desk. The only solution that seems to work is to catch the error and retry the insert until it goes fine.
Ok, so "the solution is served", but the main problem is that this way to use the "insert into" is widely used in a HUGE application with A LOT of tables and rearrange all the code where the same operation is called (declined for different tables) is something i want avoid.
Thanks for the help
解决方案
Use SERIAL instead, which is something like AUTOINCREMENT.
CREATE TABLE table_name(
id SERIAL
);
Never take COUNT+1 as two users at the same time could get the same ID, or mixed-up ID (if you use that ID further).
For good order: in a programming language like java, after inserting (without the ID) you can use getGeneratedKeys
to obtain the generated primary key.
推荐阅读
- sbt - 如何在 sbt 0.13 中动态获取子项目列表
- javascript - 从 json 数组文件中检索键(动态)并将其用于 d3js 函数
- asp.net-mvc - mvc 将模型对象作为变量传递给冗余函数
- javascript - 使用交叉点观察者设置背景图像 src 时,Safari 上的白色闪烁/闪烁?
- android - 使用 DownloadManager 在进度条中显示下载进度
- haskell - 等效于 OCaml 中的 haskell TypeError
- dax - 计算过去 30 天(不包括今天)的平均值。达克斯
- python - python-scrapy 项目返回 url 列表,并在 url 中抓取内容
- java - 如何检查 map.get(1) Java 的空集合
- excel - 从一组标签中获取特定文本的第一次出现
- 使用 VBA 的标签