Вопрос с собеседования · Spring

Что делает propagation=REQUIRES_NEW и какой подводный камень с пулом соединений он несёт?

Senior@TransactionalSpring
Ещё спрашивают так:
  • Чем REQUIRED отличается от REQUIRES_NEW?
Коротко

REQUIRES_NEW приостанавливает текущую транзакцию и открывает новую независимую — со своим соединением. На это время поток держит два соединения: при большом параллелизме пул исчерпывается, и всё зависает (дедлок на пуле).

  • REQUIRED (по умолчанию) — присоединиться к существующей или создать
  • Типичное применение — аудит или журнал ошибок, который должен сохраниться даже при откате основной
  • Пул из N соединений и N потоков в REQUIRES_NEW — каждый держит одно и ждёт второе

А ещё NESTED — точка сохранения в той же транзакции, без второго соединения

Подробно

REQUIRES_NEW нужен, когда вложенная работа должна зафиксироваться или откатиться независимо от внешней (например, запись в audit/лог, которая должна сохраниться, даже если основная транзакция откатится). Spring приостанавливает (suspend) внешнюю транзакцию и берёт ВТОРОЕ соединение под новую — поэтому в момент выполнения вложенной заняты два соединения от одного потока. На маленьком пуле (например, Hikari на 10) массовые REQUIRES_NEW могут привести к тому, что потоки держат по соединению и ждут второго — connection-pool deadlock. Плюс, как любой @Transactional через self-invocation (вызов внутри того же бина), он не сработает без прокси.

Что хотят услышать

  • Семантика REQUIRES_NEW и отличие от REQUIRED.
  • Почему нужны два соединения и как это кладёт пул.
  • Когда оправдано, альтернатива NESTED.

Частые ошибки

  • Массово использовать REQUIRES_NEW на маленьком пуле соединений.
  • Вызывать REQUIRES_NEW-метод через this (self-invocation) — прокси не перехватит.

Проверьте себя

Один верный вариант. Подумайте, потом откройте ответ.

Показать варианты и ответ
  • ✗Присоединяется к существующей транзакции, если она есть, и коммитит с ней
  • ✗Полностью отключает транзакции для метода
  • ✗Делает транзакцию только для чтения
  • ✓Приостанавливает текущую и открывает новую — на это время заняты два соединения

Что спросят дальше

  • Чем REQUIRES_NEW отличается от NESTED?
  • Почему self-invocation ломает @Transactional?

Разбор темы

Связанные вопросы

Партнёр платформы

Разбор собеседования с sotto

После собеседования sotto разбирает разговор: оценка, каждый вопрос — хорошо, частично или слабо, чего не хватило в ответе и над чем поработать к следующему разу. Первые 30 минут бесплатно.

Разбор собеседования