Учебники

PostgreSQL — LOCKS

Блокировки или эксклюзивные блокировки или блокировки записи не позволяют пользователям изменять строку или всю таблицу. Строки, измененные UPDATE и DELETE, затем автоматически блокируются исключительно на время транзакции. Это не позволяет другим пользователям изменять строку, пока транзакция не будет зафиксирована или откатана.

Единственный раз, когда пользователи должны ждать других пользователей, это когда они пытаются изменить одну и ту же строку. Если они изменяют разные строки, ожидание не требуется. Запросы SELECT никогда не должны ждать.

База данных выполняет блокировку автоматически. Однако в некоторых случаях блокировка должна контролироваться вручную. Ручная блокировка может быть выполнена с помощью команды LOCK. Это позволяет указывать тип и область блокировки транзакции.

Синтаксис для команды LOCK

Основной синтаксис команды LOCK следующий:

LOCK [ TABLE ]
name
 IN
lock_mode
  • name — Имя (возможно, дополненное схемой) существующей таблицы для блокировки. Если перед именем таблицы указано ТОЛЬКО, блокируется только эта таблица. Если не указано ТОЛЬКО, таблица и все ее дочерние таблицы (если есть) заблокированы.

  • lock_mode — режим блокировки определяет, с какими блокировками конфликтует эта блокировка. Если режим блокировки не указан, то используется ACCESS EXCLUSIVE, наиболее ограниченный режим. Возможные значения: ДОСТУП РАЗДЕЛИТЬ, СТРОИТЬ ПОДЕЛИТЬСЯ, СТРОИТЬ ЭКСКЛЮЗИВ, ПОДЕЛИТЬСЯ ОБНОВИТЬ ЭКСКЛЮЗИВ, ПОДЕЛИТЬСЯ, ПОДЕЛИТЬСЯ СТРОК ЭКСКЛЮЗИВНО, ЭКСКЛЮЗИВНО, ДОСТУП ЭКСКЛЮЗИВНО.

name — Имя (возможно, дополненное схемой) существующей таблицы для блокировки. Если перед именем таблицы указано ТОЛЬКО, блокируется только эта таблица. Если не указано ТОЛЬКО, таблица и все ее дочерние таблицы (если есть) заблокированы.

lock_mode — режим блокировки определяет, с какими блокировками конфликтует эта блокировка. Если режим блокировки не указан, то используется ACCESS EXCLUSIVE, наиболее ограниченный режим. Возможные значения: ДОСТУП РАЗДЕЛИТЬ, СТРОИТЬ ПОДЕЛИТЬСЯ, СТРОИТЬ ЭКСКЛЮЗИВ, ПОДЕЛИТЬСЯ ОБНОВИТЬ ЭКСКЛЮЗИВ, ПОДЕЛИТЬСЯ, ПОДЕЛИТЬСЯ СТРОК ЭКСКЛЮЗИВНО, ЭКСКЛЮЗИВНО, ДОСТУП ЭКСКЛЮЗИВНО.

После получения блокировка удерживается до конца текущей транзакции. Нет команды UNLOCK TABLE; блокировки всегда снимаются в конце транзакции.

ТУПИКИ

Взаимные блокировки могут возникать, когда две транзакции ожидают завершения друг друга. Хотя PostgreSQL может обнаружить их и завершить их ROLLBACK, взаимоблокировки могут быть неудобными. Чтобы ваши приложения не сталкивались с этой проблемой, проектируйте их так, чтобы они блокировали объекты в том же порядке.

Консультативные Замки

PostgreSQL предоставляет средства для создания блокировок, которые имеют значения, определенные приложением. Это так называемые консультативные блокировки . Поскольку система не обеспечивает их использование, приложение должно правильно их использовать. Консультативные блокировки могут быть полезны для стратегий блокировки, которые неудобно подходят для модели MVCC.

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

пример

Рассмотрим таблицу COMPANY, имеющую записи следующим образом:

testdb# select * from COMPANY;
 id | name  | age | address   | salary
----+-------+-----+-----------+--------
  1 | Paul  |  32 | California|  20000
  2 | Allen |  25 | Texas     |  15000
  3 | Teddy |  23 | Norway    |  20000
  4 | Mark  |  25 | Rich-Mond |  65000
  5 | David |  27 | Texas     |  85000
  6 | Kim   |  22 | South-Hall|  45000
  7 | James |  24 | Houston   |  10000
(7 rows)

В следующем примере таблица COMPANY блокируется в базе данных testdb в режиме ACCESS EXCLUSIVE. Оператор LOCK работает только в режиме транзакции —

testdb=#BEGIN;
LOCK TABLE company1 IN ACCESS EXCLUSIVE MODE;

Приведенный выше оператор PostgreSQL даст следующий результат:

LOCK TABLE

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