Что можно заблокировать с помощью пессимистической блокировки в СУБД?

«Что можно заблокировать с помощью пессимистической блокировки в СУБД?» — вопрос из категории Базы данных, который задают на 10% собеседований Java Разработчик. Ниже — развёрнутый ответ с разбором ключевых моментов.

Ответ

Пессимистическая блокировка предполагает, что конфликты при одновременном доступе к данным вероятны, и блокирует ресурсы заранее. В контексте СУБД можно заблокировать следующие объекты:

Уровни блокировки (от наиболее частых к редким):

  1. Строки (Row-level lock): Блокировка конкретных записей в таблице. Это самый распространённый и гранулярный уровень.
    // JPA (Hibernate) пример
    Employee emp = entityManager.find(Employee.class, 1L, LockModeType.PESSIMISTIC_WRITE);
  2. Страницы данных (Page-level lock): Некоторые СУБД (например, старые версии SQL Server) блокируют страницы — физические блоки данных, содержащие несколько строк.
  3. Индексы (Key-range lock): Блокировка диапазона ключей в индексе, что предотвращает фантомное чтение (phantom reads) в некоторых уровнях изоляции.
  4. Таблицы (Table-level lock): Блокировка всей таблицы. Сильно снижает параллелизм и используется редко, обычно для операций DDL (ALTER TABLE) или массовых обновлений.

Типы пессимистических блокировок в JPA:

  • PESSIMISTIC_READ: Разделяемая (shared) блокировка. Позволяет другим транзакциям читать, но не изменять заблокированные данные.
  • PESSIMISTIC_WRITE (или PESSIMISTIC_FORCE_INCREMENT): Эксклюзивная (exclusive) блокировка. Запрещает другим транзакциям как читать (в зависимости от уровня изоляции), так и изменять данные.

Важно: Блокировка удерживается до конца транзакции (commit/rollback). Неправильный порядок захвата блокировок может привести к взаимной блокировке (deadlock).