😎 Транзакции в микросервисах: Saga vs 2PC
Когда система разбита на десятки сервисов — классические транзакции через BEGIN/COMMIT уже физически не сработают. Нужны механизмы, которые обеспечат целостность данных между разными сервисами, каждый из которых живёт в своей базе и своём технологическом стеке.
Используют два подхода: Saga и 2PC. Разберём, как они устроены, где применять и какие подводные камни есть у каждого
🌀 Saga Pattern
Saga — это цепочка локальных транзакций, каждая из которых коммитится сразу. Если одна из операций падает — запускаются компенсирующие действия, откатывающие уже выполненные шаги.
Как работает
1. Сервис A создаёт заказ
2. Сервис B списывает деньги
3. Сервис C резервирует товар
4. Сервис D создаёт доставку
Если на шаге 3 ошибка — запускаются компенсации:
— отменить доставку
— снять резерв товара
— вернуть деньги
— отменить заказ
Все шаги асинхронные, с ретраями и идемпотентностью.
Два подхода Saga
1) OrchestrationЕсть “дирижёр” (Orchestrator), который знает порядок шагов
Чаще всего — отдельный сервис или компонент (советую почитать про Temporal)
2) ChoreographyСервисы сами реагируют на события друг друга
🔗 Two-Phase Commit (2PC)
2PC — классический дистрибутивный commit: все участники говорят “готов”, после чего координатор говорит “фиксируем”
Как работает
1) Phase 1: Prepare
Координатор опрашивает сервисы:
“Готовы закоммитить транзакцию?”
2) Phase 2: Commit
Если все ответили OK → отправляется COMMIT
Если хотя бы один ответил NO → ROLLBACK
Проблемы 2PC
— блокировки: участники держат транзакции в состоянии prepare
— долгая блокировка ресурсов → падение производительности
— сеть надежна и транзакции будут падать
По факту, 2PC в микросервисах почти не используют — слишком дорог и хрупок
🐗 Вывод юзаем сагу
Saga — это дефолтный способ транзакционности в микросервисах. Правда готовить сагу сложно и часто в компаниях встречаются свои реализации паттерна
🚀 Пост Guru Node.js:
@DemetraIT