TGViewer
Библиотека Go-разработчика | Golang Библиотека Go-разработчика | Golang @goproglib · 24.1K subscribers
Post #7385 2.39K
💬 События публикуются дважды

Сервис сохраняет заказ в БД и сразу публикует событие OrderCreated. Выглядит логично, но БД и очередь это две отдельные системы.

Что может произойти: БД коммитилась, но публикация упала. Заказ есть, события нет. Клиент повторяет запрос из за таймаута. Событие публикуется еще раз. Нижестоящий сервис видит два события и создает два заказа вместо одного.

➡️ Решение: Outbox паттерн

Сохраняем заказ и событие в одной БД транзакции. Отдельный диспетчер читает неотправленные события и публикует их позже. Если диспетчер упадет или повторится, событие уже в БД и не потеряется.
// В одной транзакции
BEGIN
INSERT INTO orders ...
INSERT INTO outbox ...
COMMIT

// Отдельно
func dispatchOutbox() {
events := store.GetUnsent()
for _, e := range events {
publisher.Send(e)
store.MarkSent(e.ID)
}
}


➡️ Ключевые моменты

Каждое событие должно иметь уникальный ID. Потребители должны быть идемпотентные (игнорировать дубликаты). Outbox паттерн гарантирует, что событие не потеряется, но не гарантирует ровно одну доставку. Это нормально, если потребители правильно обрабатывают дубликаты.

➡️ Что делать

Добавьте таблицу outbox. Вставляйте заказ и событие одной транзакцией. Запустите диспетчер, который периодически отправляет события из outbox. Добавьте уникальный event_id потребителям для фильтрации дубликатов.

Граница между микросервисами это самое опасное место. Outbox паттерн это простой способ сделать ее безопаснее.

📍 Навигация: Вакансии • Задачи • Собесы

🐸 Библиотека Go-разработчика

#GoToProduction
  • ❤ 4
  • 👍 4
  • 🥱 4
More from @goproglib
  1. Sep 25, 2026💡 Код работает. А data race уже есть В Go можно записать значение в одной горутине, прочи…
  2. Sep 23, 2026💥 TCP/IP: что происходит с данными в сети Когда Go-приложение отправляет данные по сети,…
  3. Sep 22, 2026🔴 Встроенные функции len, make, panic — встроенные функции Go, которые можно использовать…
  4. Sep 21, 2026🤩 Go с нуля: серия базовых шпаргалок Собрали путь от Hello, World! до goroutines, channel…
  5. Sep 20, 2026🤔 Вопрос с собеседования по Go Что выведет программа? ❤️ — [1 2 3 4 5] / [1 2 10] 🔥 — [1…
  6. Sep 19, 2026🛠 Rune — open-source IDE и terminal multiplexer на Go Rune объединяет IDE, терминал и AI-…
Threads Profile ViewerView any public Threads profile without an account.Open ThreadLook →Writing with AI? Make it sound human.Metric37 rewrites AI drafts so they read naturally. Free AI detector, 1,500 words free.Try Metric37 →