PostgreSQL
 sql >> база данни >  >> RDS >> PostgreSQL

Застой в PostgreSQL при изпълнение на UPDATE

В PostgreSQL редовете ще бъдат заключени, когато се актуализират - всъщност начинът, по който това всъщност работи е, че всеки кортеж (версия на ред) има системно поле, наречено xmin за да посочи коя транзакция направи този кортеж актуален (чрез вмъкване или актуализиране) и системно поле, наречено xmax за да посочите коя транзакция е изтекла от този кортеж (чрез актуализиране или изтриване). Когато имате достъп до данни, той проверява всеки кортеж, за да определи дали е видим за вашата транзакция, като проверява активната ви „моментна снимка“ спрямо тези стойности.

Ако изпълнявате UPDATE и кортеж, който отговаря на вашите условия за търсене, има xmin, което би го направило видимо за вашата моментна снимка и xmax на активна транзакция, той блокира, чакайки тази транзакция да завърши. Ако транзакцията, която първо е актуализирала кортежа, се върне назад, вашата транзакция се събужда и обработва реда; ако първата транзакция се извърши, вашата транзакция се събужда и предприема действия в зависимост от текущото ниво на изолация на транзакцията.

Очевидно безизходицата е резултат от това, което се случва с редове в различен ред. В RAM няма заключване на ниво ред, което може да се получи за всички редове едновременно, но ако редовете се актуализират в същия ред, не можете да имате кръговото заключване. За съжаление, предложеното IN(1, 2) синтаксисът не гарантира това. Различните сесии може да имат различни активни фактори на разходите, задача за фонов "анализ" може да промени статистиката за таблицата между генерирането на единия и другия план или може да използва seqscan и да бъде повлияна от оптимизацията на PostgreSQL, която причинява ново seqscan за да се присъедините към вече действащ и „завъртете“, за да намалите входно/изходния диск на диска.

Ако правите актуализациите една по една в същия ред, в код на приложението или с помощта на курсор, тогава ще имате само просто блокиране, а не блокиране. Като цяло обаче релационните бази данни са предразположени към неуспехи в сериализацията и е най-добре да получите достъп до тях чрез рамка, която ще ги разпознае въз основа на SQLSTATE и автоматично ще опита отново цялата транзакция от самото начало. В PostgreSQL грешката на сериализация винаги ще има SQLSTATE от 40001 или 40P01.

http://www.postgresql.org/docs/current/interactive/mvcc-intro.html




  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. защо PG::UniqueViolation:ГРЕШКА:дублираната стойност на ключа нарушава уникалното ограничение?

  2. PostgreSQL 9.1:Как да свържете редове в масив без дубликати, ПРИСЪЕДИНЕТЕ се към друга таблица

  3. Проверка на вашите PostgreSQL архиви в Docker

  4. Заявката за избор с ограничение за отместване е твърде бавна

  5. Функция RPAD() в PostgreSQL