Паттерн Outbox используется для обеспечения надежной и атомарной отправки сообщений (например, email) после создания заказа, особенно в распределённых системах. Основная проблема — гарантировать, что письмо будет отправлено ровно один раз, даже если сервис упадёт или произойдёт сбой.
Нормально ли, что отправка email блокирует создание заказа? Как это исправить?
Паттерн Outbox используется для обеспечения надежной и атомарной отправки сообщений (например, email) после создания заказа, особенно в распределённых системах.
Короткий ответ
Что ответить на собеседовании
Подробный разбор
Ответ с пояснениями
Паттерн Outbox используется для обеспечения надежной и атомарной отправки сообщений (например, email) после создания заказа, особенно в распределённых системах. Основная проблема — гарантировать, что письмо будет отправлено ровно один раз, даже если сервис упадёт или произойдёт сбой.
Вместо того, чтобы сразу отправлять email, информация о событии (например, данные для письма) записывается в отдельную таблицу — Outbox. Эта операция происходит в рамках одной транзакции с созданием заказа, что гарантирует согласованность данных.
Отдельный процесс или сервис периодически читает записи из Outbox, отправляет email и помечает запись как обработанную. Таким образом, достигается надежность и устойчивость к сбоям.
В таблице Outbox хранятся:
- Идентификатор события
- Тип события (например, "OrderCreated")
- Данные для отправки (payload), например, email, шаблон, параметры
- Статус обработки (например, "pending", "sent")
- Метаданные (время создания, время отправки и т.п.)
Пример структуры записи в Outbox:
CREATE TABLE outbox (
id UUID PRIMARY KEY,
event_type VARCHAR(255),
payload JSONB,
status VARCHAR(50) DEFAULT 'pending',
created_at TIMESTAMP,
processed_at TIMESTAMP
);