循环违反主键值

时间:2014-04-11 04:34:11

标签: function postgresql for-loop primary-key

我的部分功能如下所述。 当我执行该函数时,我收到一条错误,指出alarm_id

的主键违规
SELECT COUNT(DISTINCT exception_sub_type) INTO v_count FROM mdas.alarm_configuration;

IF v_count > 0 THEN

FOR i IN 1..v_count
LOOP

SELECT ((MAX(alarm_id))+1) INTO v_alarm_id FROM mdas.alarm_configuration;

RAISE NOTICE 'ALARM ID (%)',v_alarm_id;

INSERT INTO mdas.alarm_configuration
    (alarm_id,
     exception_sub_type,
     exception_type,
     from_range,
     groups,
     priority,
     sub_group,
     to_range,
     org_unit_id,
     status)

SELECT DISTINCT ON(exception_sub_type) v_alarm_id,
exception_sub_type,
exception_type,
from_range,
v_group_name,
priority,
v_subgroup_name,
to_range,
v_org_unit_id,
status
FROM mdas.alarm_configuration 
WHERE groups = v_group_name AND mdas.alarm_configuration.org_unit_id = v_org_unit_id;

END LOOP;   

END IF;

注意:这只是该功能的一部分。该函数有三个参数v_org_unit_id,v_group_name和v_subgroup_name。我的主键是alarm_id,我想增加1并根据表中提供的MAX插入。

1 个答案:

答案 0 :(得分:1)

在您的环境中,当两个以上的客户端同时调用该函数时,它们将看到相同的alarm_id,因此引发了唯一的违反。 对于exp:

SESSION A : 
select max(id) into v_id from test;
insert into test values (v_id);
.. not end else.

SESSION B : 
select max(id) into v_id from test;   -- this v_id will same as session a.
insert into test values (v_id);

and then session A commit;
SESSION B will raise error.
ERROR:  duplicate key value violates unique constraint "test_pkey"
DETAIL:  Key (id)=(?) already exists.

你可以使用PostgreSQL串口处理这个问题。 喜欢:

digoal=# create table test (id serial primary key, other_cols type ...);
CREATE TABLE

并且不需要使用max(id),您只需要键入其他列的值。 像

insert into test (other_cols,...) values (...);