увеличение ошибок - PullRequest
       4

увеличение ошибок

2 голосов
/ 30 марта 2011

Как подавить увеличение идентификатора в этой таблице при возникновении ошибки?

db=> CREATE TABLE test (id serial primary key, info text, UNIQUE(info));
NOTICE:  CREATE TABLE will create implicit sequence "test_id_seq" for serial column "test.id"
NOTICE:  CREATE TABLE / PRIMARY KEY will create implicit index "test_pkey" for table "test"
NOTICE:  CREATE TABLE / UNIQUE will create implicit index "test_info_key" for table "test"
CREATE TABLE

db=> INSERT INTO test (info) VALUES ('hello') ;
INSERT 0 1

db=> INSERT INTO test (info) VALUES ('hello') ;
ERROR:  duplicate key violates unique constraint "test_info_key"

db=> INSERT INTO test (info) VALUES ('hello') ;
ERROR:  duplicate key violates unique constraint "test_info_key"

db=> INSERT INTO test (info) VALUES ('goodbye') ;
INSERT 0 1

db=> SELECT * from test; SELECT last_value from test_id_seq;

 id |  info   
----+---------
  1 | hello
  4 | goodbye
(2 rows)

 last_value 
------------
          4
(1 row)

Ответы [ 4 ]

6 голосов
/ 31 марта 2011

Вы не можете подавить это - и нет ничего плохого в том, что в ваших значениях ID есть пробелы.

Первичный ключ - это абсолютно бессмысленное значение, которое используется только для однозначной идентификации одной строки в таблице.

Вы не можете полагаться на идентификатор, чтобы никогда не иметь пробелов - просто подумайте, что произойдет, если вы удалите строку.

Просто игнорируйте это - ничего плохого

Редактировать Просто хотел отметить, что это поведение также четко указано в руководстве:

Чтобы избежать блокирования параллельных транзакций, которые получают числа из той же последовательности, операция nextval никогда не откатывается

http://www.postgresql.org/docs/current/static/functions-sequence.html
(Прокрутите вниз)

2 голосов
/ 31 марта 2011

Ваш вопрос сводится к следующему: «Могу ли я откатить следующее значение из последовательности PostgreSQL?»

И ответ: «Вы не можете». Документация PostgreSQL гласит

Чтобы избежать блокировки параллельных транзакций, которые получают числа из той же последовательности, операция nextval никогда не откатывается. , .

1 голос
/ 31 марта 2011

Представьте, что две разные транзакции идут на вставку. Транзакция A получает id = 1 Транзакция B получает id = 2. Транзакция B фиксирует. транзакция А откатывается. Теперь, что мы делаем? Как мы можем откатить последовательность для A, не влияя на B или более поздние транзакции?

0 голосов
/ 01 апреля 2011

Я понял это.

Мне нужно было написать функцию-оболочку для моего оператора INSERT.

В базе данных обычно будет по одному пользователю за раз, поэтому условие «переход к следующему идентификатору» встречается редко. Что меня беспокоило, так это то, что моя (не упомянутая) функция «извлекать строки из таблицы удаленной базы данных» попыталась повторно вставить растущую таблицу удаленной базы данных в основную таблицу базы данных. Я отображаю идентификаторы строк, и я не хотел, чтобы пользователи рассматривали разрыв в нумерации как отсутствующие данные.

В любом случае, вот мое решение:

CREATE FUNCTION testInsert (test.info%TYPE) RETURNS void AS '
BEGIN
  PERFORM info FROM test WHERE info=$1;
  IF NOT FOUND THEN
    INSERT INTO test (info) VALUES ($1);
  END IF;
END;' LANGUAGE plpgsql;
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...