PostgreSQL
 sql >> Baza danych >  >> RDS >> PostgreSQL

Ograniczenie zdefiniowane ODROCZONY POCZĄTKOWO NATYCHMIAST jest nadal ODROCZONY?

Pamiętam, że podniosłem prawie identyczny punkt, gdy PG9 był w stanie alfa. Oto odpowiedź od Toma Lane'a (znanego programisty rdzenia PG):
http://archives.postgresql.org/pgsql-general/2010-01/msg00221.php

W skrócie:nie naprawi.

Nie mówię, że zgadzam się z twoją sugestią, że obecne zachowanie jest błędem. Spójrz na to z przeciwnej strony:to zachowanie NOT DEFERRABLE to jest niepoprawne.

W rzeczywistości naruszenie ograniczenia w tej aktualizacji nigdy nie powinno mieć miejsca, ponieważ pod koniec aktualizacji ograniczenie jest spełnione. Liczy się stan na końcu polecenia. Stany pośrednie podczas wykonywania pojedynczej instrukcji nie powinny być ujawniane użytkownikowi.

Wygląda na to, że PostgreSQL implementuje nieodroczalne ograniczenie, sprawdzając, czy nie ma duplikatów po każdym zaktualizowaniu każdego wiersza, i zawodzi natychmiast po pierwszym duplikacie, co jest zasadniczo wadliwe. Ale jest to znany problem, prawdopodobnie tak stary jak PostgreSQL. Obecnie obejście tego problemu polega właśnie na użyciu ograniczenia ODROCZENIA. I jest pewna ironia w tym, że patrzysz na to jako na niedoskonałe, ponieważ nie zawodzi, podczas gdy jakoś ma być rozwiązaniem niepowodzenia!

Podsumowanie status quo od czasu PostgreSQL 9.1

  • NOT DEFERRABLE UNIQUE lub PRIMARY KEY ograniczenia są sprawdzane po każdym wierszu .

  • DEFERRABLE ograniczenia ustawione na IMMEDIATE (INITIALLY IMMEDIATE lub przez SET CONSTRAINTS ) są sprawdzane po każdym oświadczeniu .

  • DEFERRABLE ograniczenia ustawione na DEFERRED (INITIALLY DEFERRED lub przez SET CONSTRAINTS ) są sprawdzane po każdej transakcji .

Zwróć uwagę na specjalne traktowanie UNIQUE / PRIMARY KEY ograniczenia. Cytując stronę podręcznika dla CREATE TABLE :

Ograniczenie, którego nie można odroczyć, zostanie sprawdzone natychmiast po każdym poleceniu .

Chociaż jest to opisane dalej w sekcji Zgodność sekcja w sekcji Non-deferred uniqueness constraints :

Gdy UNIQUE lub PRIMARY KEY ograniczenia nie można odroczyć, PostgreSQL od razu sprawdza unikalność za każdym razem, gdy wiersz jest wstawiany lub modyfikowany. Standard SQL mówi, że unikalność powinna być wymuszana tylko na końcu instrukcji; robi to różnicę, gdy na przykład jedno polecenie aktualizuje wiele wartości kluczy. Aby uzyskać zachowanie zgodne ze standardami, zadeklaruj ograniczenie jako DEFERRABLE ale nie odroczone (np. INITIALLY IMMEDIATE ). Pamiętaj, że może to być znacznie wolniejsze niż natychmiastowe sprawdzanie unikalności.

Pogrubiony nacisk na moje.

Jeśli potrzebujesz FOREIGN KEY ograniczenia do odwoływania się do kolumn, DEFERRABLE nie jest opcją, ponieważ (zgodnie z dokumentacją):

Kolumny, do których się odwołują, muszą być kolumnami nieodroczonego ograniczenia unikalności lub klucza podstawowego w tabeli, do której się odwołują.



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Zwróć wiersze SETOF z funkcji PostgreSQL

  2. Importuj dane z Excela do PostgreSQL 9.3

  3. Konfigurowanie optymalnego środowiska dla PostgreSQL

  4. Jak zresetować domyślne hasło użytkownika postgresql 9.2 (zwykle „postgres”) w systemie Mac OS x 10.8.2?

  5. Jak zaktualizować bazę danych postgresql z 10 do 12 bez utraty danych dla openproject?