Как стать автором
Обновить
582.82
OTUS
Цифровые навыки от ведущих экспертов

Практическое руководство по выбору брокера сообщений

Уровень сложностиСредний
Время на прочтение21 мин
Количество просмотров3K
Автор оригинала: Nehme Bilal, Thomas Betts
Ключевые выводы
  • Существует два основных типа брокеров сообщений — потоковые (streaming) и очередные (queue‑based), в зависимости от модели обработки данных. Каждый тип имеет свои преимущества и характерные компромиссы в использовании.

  • Сообщения в потоке отслеживаются с помощью смещений (offsets), что позволяет консюмерам (consumers, потребители) эффективно коммитить большие пакеты (batches) за один сетевой вызов и воспроизводить сообщения, перемещая смещение назад. В отличие от этого, очереди имеют ограниченные возможности для пакетной обработки и, как правило, не позволяют повторно воспроизводить сообщения, так как те удаляются после обработки.

  • Потоковые решения используют фиксированные физические партиции для масштабирования, что создаёт сложности при обработке «ядовитых» (необрабатываемых) сообщений и ограничивает возможность динамического авто‑масштабирования консюмеров при колебаниях трафика. Очереди, такие как Amazon SQS и FIFO SQS, используют логические партиции с низкой кардинальностью (упорядоченные), что обеспечивает бесшовное авто‑масштабирование и эффективную изоляцию «ядовитых» сообщений (poison pills).

  • Потоковые брокеры идеально подходят для сценариев репликации данных, поскольку обеспечивают эффективную пакетную обработку и в целом менее подвержены «ядовитым» сообщениям.

  • Когда пакетная репликация не требуется, очереди, такие как Amazon SQS или FIFO SQS, часто становятся более подходящим выбором, так как они поддерживают авто‑масштабирование, изолируют «ядовитые» сообщения и при необходимости обеспечивают упорядоченную (FIFO) обработку.

  • Комбинирование потоков и очередей позволяет организациям стандартизировать производство сообщений на одном потоковом решении, одновременно предоставляя консюмерам гибкость — либо читать сообщения напрямую из потока, либо направлять их в очередь в зависимости от используемого шаблона обмена сообщениями.

Решения для обмена сообщениями играют важную роль в современных распределённых системах. Они обеспечивают надёжную коммуникацию, поддерживают асинхронную обработку и способствуют слабой связности между компонентами. Кроме того, они повышают доступность приложений и помогают защитить системы от всплесков трафика. Существующие варианты охватывают как потоковые, так и очередные сервисы, каждый из которых предлагает собственные преимущества и компромиссы.

Основываясь на своем опыте работы с различными инженерными командами, могу сказать, что выбор брокера сообщений редко осуществляется по чётко выработанной методологии. На решение чаще влияют тренды, личные предпочтения или простота доступа к конкретной технологии, а не реальные потребности приложения. Однако при выборе брокера ключевым должно быть соответствие его характеристик требованиям приложения — именно этому и посвящена данная статья.

Мы рассмотрим два самых популярных решения в этой области: Apache Kafka (потоковое) и Amazon SQS (очередное). Продемонстрировав, насколько их свойства соответствуют типичным шаблонам обмена сообщениями, статья поможет вам принимать более обоснованные решения. Это понимание станет основой для оценки других сценариев и брокеров — и в конечном итоге позволит выбрать оптимальный вариант для вашего приложения

Брокеры сообщений

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

Amazon SQS (Simple Queue Service)

Amazon SQS — это полностью управляемый сервис очередей сообщений, который упрощает взаимодействие между слабо связанными компонентами в распределённых системах. Он обеспечивает надёжную доставку сообщений, абстрагируя сложности управления инфраструктурой, масштабирования и обработки ошибок. Ниже перечислены ключевые свойства Amazon SQS.

Управление жизненным циклом сообщений
В SQS жизненный цикл сообщений в SQS управляется либо по одному, либо небольшими пакетами до 10 сообщений. Каждое сообщение может быть получено, обработано, удалено или даже отложено в зависимости от потребностей приложения. Обычно приложение получает сообщение, обрабатывает его и затем удаляет из очереди, что гарантирует надёжную обработку сообщений.

Порядок доставки по принципу best‑effort
Стандартные очереди SQS доставляют сообщения в том порядке, в котором они были отправлены, но не гарантируют строгого соблюдения порядка, особенно при повторных попытках или параллельном потреблении. Это позволяет достигать высокой пропускной способности, когда строгий порядок обработки не критичен. Для случаев, где порядок важен, можно использовать FIFO SQS, который гарантирует обработку сообщений в заданной последовательности.

Встроенная очередь «мёртвых» писем (DLQ)
SQS из коробки поддерживает Dead Letter Queue (DLQ), которая помогает изолировать «ядовитые» сообщения.

Пропускная способность на запись и чтение
SQS поддерживает практически неограниченную пропускную способность на запись и чтение, что делает его подходящим для высоконагруженных приложений, где важно эффективно обрабатывать большие объёмы сообщений.

Автомасштабирование консюмеров
SQS поддерживает авто‑масштабирование вычислительных ресурсов (таких как AWS Lambda, EC2 или ECS) на основе количества сообщений в очереди (см. официальную документацию). Консюмеры могут динамически масштабироваться для обработки возросшего трафика и снижать масштаб при уменьшении нагрузки. Эта возможность авто‑масштабирования позволяет приложениям обрабатывать переменную нагрузку без ручного вмешательства, что крайне ценно при работе с непредсказуемыми пиковыми нагрузками.

Поддержка pub/sub
Нативно SQS не поддерживает модель издатель‑подписчик (publisher‑subscriber; pub/sub), так как изначально предназначен для point‑to‑point взаимодействия, где каждое сообщение потребляется одним получателем. Однако реализовать pub/sub архитектуру можно, интегрировав SQS с Amazon Simple Notification Service (SNS). SNS позволяет публиковать сообщения в топик, который затем рассылает их в несколько очередей SQS, подписанных на этот топик. Это позволяет нескольким консюмерам независимо получать и обрабатывать одно и то же сообщение, фактически реализуя pub/sub на базе сервисов AWS.

Amazon FIFO SQS

FIFO SQS является расширенной версией стандартной SQS, гарантируя строгий порядок обработки сообщений внутри каждой логической партиции, называемой группой сообщений. Этот тип очереди идеально подходит для рабочих процессов, требующих последовательной обработки связанных событий — например, персонализированных уведомлений для пользователей, финансовых транзакций или любых сценариев, в которых критично сохранять точный порядок сообщений. Ниже рассмотрим ключевые особенности FIFO SQS.

Группировка сообщений как логические партиции
В FIFO SQS каждое сообщение содержит параметр MessageGroupId, который определяет логическую партицию внутри очереди. Все сообщения с одинаковым MessageGroupId обрабатываются последовательно. Это обеспечивает строгий порядок обработки внутри конкретной группы сообщений, тогда как сообщения из разных групп могут обрабатываться параллельно разными консюмерами. Например, в ситуации, когда сообщения для каждого пользователя должны обрабатываться в определённом порядке (например, последовательность уведомлений или действий), присвоение каждому пользователю уникального MessageGroupId гарантирует, что все его сообщения в рамках этой группы будут обрабатываться строго по порядку, независимо от времени их попадания в очередь.

Сообщения других пользователей (с другим MessageGroupId) могут обрабатываться параллельно, что позволяет сохранить высокую пропускную способность без ущерба для порядка сообщений конкретного пользователя. Это даёт FIFO SQS существенное преимущество по сравнению со стандартной SQS или потоковыми брокерами сообщений, такими как Apache Kafka и Amazon Kinesis.

Dead Letter Queue (DLQ)
FIFO SQS имеет встроенную поддержку очередей для сообщений, которые не удалось обработать (DLQ), однако их использование требует особого внимания, так как перенос сообщений в DLQ может нарушить строгий порядок сообщений в рамках одной группы.

Например, если два сообщения — message1 и message2 — принадлежат одной группе (MessageGroupId = groupA), и message1 не удаётся обработать и оно переносится в DLQ, то message2 может быть успешно обработано. Это нарушает предполагаемый порядок сообщений в группе и сводит на нет ключевое преимущество FIFO‑обработки.

Изоляция «ядовитых» сообщений (poison pills)
Если DLQ не используется, FIFO SQS будет продолжать бесконечно пытаться доставить проблемное сообщение. Это сохраняет порядок, но может привести к возникновению узкого места, заблокировав обработку всех последующих сообщений в той же группе, пока сбойное сообщение не будет успешно обработано или удалено.

Повторно неудачно обрабатываемые сообщения называют «ядовитыми» (poison pills). В некоторых системах такие сообщения могут заблокировать всю очередь или шарду, остановив обработку остальных сообщений. Однако в FIFO SQS их влияние ограничено только соответствующей группой сообщений (логической партицией), к которой они принадлежат. Такая изоляция значительно снижает масштаб последствий, при условии, что группы сообщений продуманы и сконфигурированы правильно.

Чтобы минимизировать сбои, важно выбирать MessageGroupId таким образом, чтобы логические партиции оставались небольшими, но при этом упорядоченные сообщения находились в пределах одной группы. Например, в многопользовательском приложении использование идентификатора пользователя в качестве MessageGroupId обеспечит, что сбой затронет только сообщения конкретного пользователя. Аналогично, в e‑commerce‑сценарии использование ID заказа позволит сбойному сообщению не повлиять на заказы других клиентов.

Для иллюстрации эффекта изоляции рассмотрим сценарий с poison pill:

  • Без изоляции (или с изоляцией только на уровне шарды) одно «ядовитое» сообщение может заблокировать все заказы в целом регионе (например, все заказы Amazon.com в одной стране).

  • С изоляцией в FIFO SQS будет затронут только заказ одного пользователя, а остальные продолжат обрабатываться как обычно.

Таким образом, изоляция «ядовитых» сообщений — это крайне важная особенность FIFO SQS, существенно повышающая устойчивость распределённых систем обмена сообщениями.

Пропускная способность
По умолчанию FIFO SQS ограничена 300 сообщениями в секунду. Однако при включении режима высокой пропускной способности это ограничение можно увеличить до 9000 сообщений в секунду. Для достижения такой производительности требуется тщательно спроектировать группы сообщений, чтобы обеспечить достаточный уровень параллелизма.

Автомасштабирование консюмеров
Подобно стандартной SQS, FIFO SQS поддерживает авто‑масштабирование вычислительных ресурсов на основе количества сообщений в очереди. Хотя масштабируемость FIFO SQS не является абсолютно неограниченной, она зависит от числа групп сообщений (логических партиций), которых может быть очень много (например, одна группа на пользователя).

Поддержка pub/sub
Как и в случае со стандартной SQS, модель pub/sub можно реализовать, объединив FIFO SQS с SNS, который поддерживает FIFO‑топики.

Apache Kafka

Apache Kafka — это платформа потоковой передачи данных с открытым исходным кодом, предназначенная для стриминга событий в реальном времени и обработки данных с высокой пропускной способностью. В отличие от традиционных очередей сообщений, таких как SQS, Kafka работает как система потоковой передачи данных, где сообщения потребляются на основе смещений (offsets). В Kafka консюмеры отслеживают прогресс, сдвигая своё смещение вперёд (или назад — для повторного воспроизведения), что позволяет коммитить сразу несколько сообщений за один шаг. Такой подход с использованием смещений является ключевым отличием Kafka от традиционных очередей, в которых каждое сообщение обрабатывается и подтверждается отдельно. Ниже описаны основные свойства Kafka.

Физические партиции (шарды)
Топики Kafka разбиваются на физические партиции (также называемые шардой) при их создании. Каждая партиция поддерживает своё собственное смещение и порядок сообщений независимо от других партиций. Партиции можно добавлять, но это может повлиять на распределение данных и потребовать аккуратной настройки. Уменьшение количества партиций ещё сложнее и, как правило, не рекомендуется, так как влияет на распределение данных и балансировку нагрузки между консюмерами. Поскольку схема партиционирования напрямую влияет на масштабируемость и производительность, её необходимо тщательно продумывать с самого начала.

Поддержка pub/sub
Kafka изначально поддерживает модель pub/sub. Это позволяет нескольким группам консюмеров независимо обрабатывать один и тот же топик, благодаря чему разные приложения или сервисы могут потреблять одни и те же данные без взаимного влияния. Каждая группа консюмеров имеет собственный вид на топик, что обеспечивает гибкость в масштабировании как продюсеров (producers, поставщики), так и консюмеров.

Высокая пропускная способность и пакетная обработка
Kafka оптимизирована для сценариев с высокой нагрузкой, что обеспечивает эффективную обработку больших объёмов данных. Консюмеры могут обрабатывать крупные пакеты сообщений, сокращая количество операций чтения и записи. Например, консюмер может обработать до 10 000 сообщений, сохранить их в базу данных одной операцией и затем коммитить смещение одним действием, что значительно снижает издержки. Это является ключевым отличием потоков от очередей, где сообщения обрабатываются поодиночке или небольшими пакетами.

Возможность воспроизведения (replay)
Kafka хранит сообщения в течение настраиваемого периода хранения (по умолчанию — 7 дней), позволяя консюмерам «перематывать» и повторно воспроизводить сообщения. Это особенно полезно для отладки, повторной обработки исторических данных или восстановления после ошибок приложения. Консюмеры могут обрабатывать данные в собственном темпе и повторно запрашивать сообщения при необходимости, что делает Kafka отличным выбором для задач, требующих надёжности и отказоустойчивости.

Обработка «ядовитых» сообщений
В Kafka «ядовитое» сообщение может заблокировать всю физическую партицию, в которой оно находится, задерживая обработку всех последующих сообщений в этой партиции. Это может иметь серьёзные последствия для приложения. Например, в e‑commerce‑сценарии, где заказы из одного региона обрабатываются через выделенную шард Kafka, одно проблемное сообщение может заблокировать все заказы этого региона, приведя к серьёзным сбоям в бизнесе. Это ограничение подчёркивает важный недостаток жёсткого физического партиционирования по сравнению с логическим партиционированием в очередях, таких как FIFO SQS, где сбои изолированы в рамках небольшой группы сообщений, а не всей партиции.

Если строгий порядок не требуется, использование Dead Letter Queue может помочь уменьшить влияние таких сообщений, изолируя их и предотвращая блокировку всей обработки.

Ограничения автомасштабирования
Масштабирование Kafka ограничено моделью физического партиционирования: каждая партиция поддерживает строгий порядок и может обрабатываться только одним вычислительным узлом одновременно. Это означает, что добавление дополнительных узлов, превышающее количество партиций, не увеличит пропускную способность — лишние узлы будут простаивать. В результате Kafka плохо сочетается с автоматическим масштабированием консюмеров, так как их количество по сути ограничено числом партиций. Это делает Kafka менее гибкой в динамических сценариях масштабирования по сравнению с системами обмена сообщениями, такими как FIFO SQS, где логическое партиционирование позволяет более точно масштабировать консюмеров.

Сравнение брокеров сообщений

Характеристика

Standard SQS

FIFO SQS

Apache Kafka

Срок хранения сообщений

До 14 дней

До 14 дней

Настраивается (по умолчанию: 7 дней)

Поддержка Pub‑Sub

через SNS

через SNS

Нативная через группы консюмеров

Порядок сообщений

Порядок доставки по принципу best‑effort

Гарантирован внутри группы сообщений

Гарантирован внутри физической партиции (шарды)

Пакетная обработка

Поддержка пакетов до 10 сообщений

Поддержка пакетов до 10 сообщений

Эффективные крупные пакетные коммиты

Пропускная способность записи

Практически неограниченная

300 сообщений/сек на группу сообщений

Масштабируется через физические партиции (возможно миллионы сообщений в секунду)

Пропускная способность чтения

Неограниченная

300 сообщений/сек на группу сообщений

Масштабируется через физические партиции (возможно миллионы сообщений в секунду)

Поддержка DLQ

Встроена

Встроена, но может нарушить порядок

Поддерживается через коннекторы, но может нарушить порядок в партиции

Изоляция «ядовитых» сообщений

Изолированы на уровне отдельных сообщений

Изолированы на уровне групп сообщений

Может заблокировать всю физическую партицию

Возможность воспроизведения

Не поддерживается

Не поддерживается

Поддерживается через перемотку смещений (offset rewinding)

Автомасштабирование консюмеров

Неограниченное

Ограничено числом групп сообщений (почти неограничено на практике)

Ограничено числом физических партиций (шардов)

Шаблоны обмена сообщениями и их влияние на выбор брокера

В распределённых системах шаблоны обмена сообщениями определяют, как сервисы взаимодействуют между собой и обрабатывают информацию. Каждый шаблон предъявляет уникальные требования — например, к порядку обработки, масштабируемости, обработке ошибок или параллельной обработке, — что влияет на выбор подходящего брокера сообщений. В данном разделе рассматриваются три распространённых шаблона: Command Pattern, Event‑Carried State Transfer (ECST) и Event Notification Pattern, а также анализируется, насколько их особенности соответствуют возможностям популярных брокеров, таких как Amazon SQS и Apache Kafka. Этот подход также можно применить для оценки других шаблонов обмена сообщениями и выбора наилучшего брокера под конкретные задачи.

Command Pattern

Command Pattern — это подход к проектированию, при котором запросы или действия представляются в виде самостоятельных объектов‑команд. Эти команды отправляются брокеру сообщений для асинхронной обработки, что позволяет отправителю продолжать выполнение своих задач без ожидания ответа.

Такой шаблон повышает надёжность: команды можно сохранять и повторно отправлять при сбоях. Он также увеличивает доступность продюсера, позволяя ему работать даже при недоступности консюмеров. Кроме того, шаблон защищает консюмеров от всплесков трафика, позволяя им обрабатывать команды в собственном темпе.

Поскольку обработка команд часто включает сложную бизнес‑логику, операции с базой данных и вызовы внешних API, успешная реализация требует надёжности, параллельной обработки, автомасштабирования и эффективной работы с «ядовитыми» сообщениями.

Ключевые характеристики

Несколько источников, один получатель
Команды могут создаваться одним или несколькими сервисами, но потребляются обычно только одним сервисом. Каждая команда обрабатывается лишь один раз, при этом несколько узлов‑консюмеров конкурируют за команды. В результате поддержка pub/sub для команд не требуется.

Высокая пропускная способность
Команды могут генерироваться с высокой скоростью несколькими продюсерами, поэтому брокер сообщений должен обеспечивать не только высокую пропускную способность, но и надёжную доставку с низкой задержкой, чтобы отправка команд не становилась узким местом для вышестоящих сервисов.

Автомасштабирование консюмеров
На стороне консюмера обработка команд часто включает трудоёмкие задачи, такие как запись в базу данных и вызовы внешних API. Чтобы избежать конфликтов и перегрузок, необходима параллельная обработка команд. Выбранный брокер должен позволять консюмерам получать команды параллельно и обрабатывать их независимо, не ограничиваясь малым числом параллельных потоков (например, физическими партициями). Это позволяет горизонтально масштабироваться для работы с пиками нагрузки, а также снижать ресурсы при низкой активности для оптимизации затрат.

Риск «ядовитых» сообщений
Обработка команд часто включает сложные процессы и вызовы внешних сервисов, что увеличивает вероятность сбоев и появления «ядовитых» сообщений, которые могут блокировать дальнейшую обработку. Чтобы минимизировать влияние, брокер сообщений должен поддерживать высокую кардинальность изоляции таких сообщений — то есть сбой должен затрагивать только небольшую часть команд, а не всю систему. Изолируя «ядовитые» сообщения в отдельных группах или партициях, система сохраняет надёжность и продолжает эффективно обрабатывать остальные команды.

Соответствие брокеров шаблону

С учётом требований к параллельному потреблению, автомасштабированию и изоляции «ядовитых» сообщений Kafka не является оптимальным выбором для обработки команд. Как уже упоминалось, фиксированное число физических партиций в Kafka нельзя масштабировать динамически. Более того, одно «ядовитое» сообщение может заблокировать всю партицию, потенциально нарушив работу большого числа пользователей приложения.

Если порядок обработки не критичен, стандартная SQS отлично подойдёт для потребления и обработки команд. Она поддерживает параллельную обработку с неограниченной пропускной способностью, динамическое масштабирование и возможность изолировать «ядовитые» сообщения с помощью DLQ.

Для сценариев, где требуется сохранение порядка и его можно распределить между множеством логических партиций, FIFO SQS является оптимальным решением. При стратегическом выборе MessageGroupId можно создать множество небольших логических партиций и добиться практически неограниченного параллелизма и пропускной способности. Кроме того, любое «ядовитое» сообщение повлияет только на одну логическую партицию (например, сообщения одного пользователя), обеспечивая минимальное и изолированное влияние на остальную систему.

Event-carried State Transfer (ECST)

Шаблон Event‑carried State Transfer (ECST) — это шаблон проектирования, применяемый в распределённых системах для репликации данных и децентрализованной обработки. В этом шаблоне события выступают в роли основного механизма передачи изменений состояния между сервисами. Каждое событие содержит всю необходимую информацию (состояние), чтобы другие компоненты могли обновить свои локальные копии состояния без необходимости синхронных обращений к исходному сервису.

Благодаря отделению сервисов друг от друга и снижению зависимости от коммуникации в реальном времени, ECST повышает устойчивость системы, позволяя компонентам работать независимо, даже если отдельные части системы временно недоступны. Кроме того, ECST снижает нагрузку на исходную систему, реплицируя данные туда, где они действительно нужны. Сервисы могут опираться на локальные копии состояния, вместо того чтобы постоянно обращаться к исходному источнику через API. Этот шаблон особенно полезен в архитектурах, основанных на событиях (event‑driven), и в сценариях, где допустима согласованность со временем.

Ключевые характеристики

Один источник, несколько получателей
В ECST события публикуются владельцем состояния и потребляются несколькими сервисами или компонентами, которым необходимо получить копию состояния. Это требует от брокера сообщений поддержки модели pub/sub.

Низкая вероятность появления «ядовитых» сообщений
Поскольку ECST почти не включает бизнес‑логику и, как правило, не использует вызовы внешних API, риск появления «ядовитых» сообщений минимален. В результате в этом шаблоне необходимость использования Dead Letter Queue (DLQ) практически отсутствует.

Пакетная обработка
Поскольку ECST включает репликацию данных, этот шаблон особенно выигрывает от пакетной обработки. Репликация данных крупными пакетами повышает производительность и снижает затраты, особенно если целевая база данных поддерживает массовые вставки данных за один запрос. Брокер сообщений, поддерживающий эффективные пакетные коммиты, в сочетании с базой данных, оптимизированной под пакеты, может значительно повысить производительность приложения.

Строгий порядок
В ECST строгий порядок сообщений часто является обязательным, чтобы изменения состояния сущности применялись в правильной последовательности. Это предотвращает перезапись более новой версии сущности старой. Порядок особенно критичен, когда события передают дельты (например, «установить свойство X»), поскольку события, полученные вне порядка, не могут быть просто проигнорированы. Брокер, поддерживающий строгую упорядоченность, существенно упрощает потребление событий и гарантирует целостность данных.

Соответствие брокеров шаблону

С учётом требований к pub/sub, строгому порядку и пакетной обработке, а также низкой вероятности появления «ядовитых» сообщений, Apache Kafka является отличным выбором для реализации ECST.

Kafka позволяет консюмерам обрабатывать большие пакеты сообщений и фиксировать смещения за один шаг. Например, 10 000 событий можно обработать и записать в базу данных одним пакетом (при условии, что база это поддерживает) и зафиксировать с помощью одного сетевого вызова — это делает Kafka гораздо более эффективным, чем Amazon SQS в таких сценариях. Кроме того, минимальный риск «ядовитых» сообщений устраняет необходимость в DLQ, упрощая обработку ошибок. Помимо поддержки пакетов, механизм партиционирования Kafka позволяет повышать пропускную способность путём распределения событий по нескольким шардам.

Однако, если целевая база данных не поддерживает обработку пакетами, то именно она станет узким местом, и преимущество Kafka в пакетных коммитах теряет значение. В таких случаях может быть эффективнее направлять сообщения из Kafka в FIFO SQS или использовать FIFO SNS/SQS без Kafka. Как уже упоминалось ранее, FIFO SQS позволяет реализовать гибкую настройку логических партиций, обеспечивая параллельную обработку при сохранении порядка сообщений. Такая архитектура поддерживает динамическое масштабирование за счёт увеличения числа консюмеров для обработки пиков трафика, обеспечивая эффективную обработку даже при высоких нагрузках.

Event Notification Pattern

Шаблон Event Notification Pattern позволяет сервисам уведомлять другие сервисы о значимых событиях, происходящих в системе. Уведомления, как правило, легковесны и содержат минимально необходимую информацию (например, идентификатор), чтобы описать событие. Для обработки уведомления консюмерам часто необходимо извлечь дополнительные данные из источника (и/или других сервисов) с помощью вызовов API. Кроме того, консюмеры могут выполнять обновления в базе данных, генерировать команды или публиковать уведомления для других систем.

Этот шаблон способствует слабой связности компонентов и обеспечивает быструю реакцию в рамках распределённой архитектуры. Однако, учитывая потенциальную сложность обработки уведомлений (например, вызовы API, обновление БД, публикация новых событий), масштабируемость и надёжная обработка ошибок крайне важны.

Ключевые характеристики

Характеристики шаблона Event Notification Pattern во многом пересекаются с шаблоном команд (Command Pattern), особенно в тех случаях, когда обработка уведомлений включает сложные и ресурсоёмкие задачи. В таких сценариях реализация шаблона требует поддержки параллельного потребления, автомасштабирования консюмеров и изоляции «ядовитых» сообщений, чтобы обеспечить надёжную и эффективную обработку. Кроме того, шаблон Event Notification требует поддержки pub/sub для реализации схемы «один ко многим».

Однако бывают случаи, когда обработка уведомлений сводится к простым действиям — например, обновлению базы данных или публикации событий в другие системы. В таких ситуациях характеристики шаблона ближе к шаблону ECST.

Также важно учитывать, что разные консюмеры одного и того же уведомления могут обрабатывать его по‑разному. Один консюмер может выполнять сложную бизнес‑логику, в то время как другой ограничивается простыми действиями, которые почти никогда не приводят к сбоям.

Соответствие брокеров используемым шаблонам

Если характеристики потребления уведомлений соответствуют обработке команд, то SQS (или FIFO SQS) — очевидный выбор. Однако если консюмеру нужно лишь выполнять простые обновления в базе данных, то Kafka может быть более эффективным решением благодаря возможности пакетной обработки уведомлений и фиксации обработанных сообщений одним действием.

Сложность с уведомлениями заключается в том, что заранее предсказать, как именно будут потребляться сообщения, невозможно. Это затрудняет выбор между SNS и Kafka при публикации уведомлений.

Чтобы обеспечить гибкость, мы в своей компании приняли решение использовать Kafka как единственный брокер для публикации уведомлений. Если консюмеру нужны свойства, присущие SQS, сообщения из Kafka можно направить в SQS через AWS EventBridge. Если таких требований нет, консюмер может читать уведомления напрямую из Kafka и использовать преимущества пакетной обработки. Более того, использование Kafka вместо SNS позволяет консюмерам воспользоваться возможностью воспроизведения сообщений, даже если они были перенаправлены в SQS.

Кроме того, учитывая, что Kafka также отлично подходит для шаблона ECST, а шаблон команд не требует Pub/Sub, у нас не осталось причин использовать SNS. Это позволило принять Kafka в качестве единственного брокера для Pub/Sub, что значительно упростило наши процессы. Фактически, поскольку все события проходят через Kafka, мы смогли создать инструменты для репликации событий Kafka в DataLake, который используется для отладки, аналитики, повторной обработки, восполнения данных (backfilling) и других целей.

Заключение

Выбор подходящего брокера сообщений для вашего приложения требует понимания характеристик доступных решений и используемого шаблона обмена сообщениями. Ключевые факторы, которые следует учитывать:

 — тип трафика,
 — возможность авто‑масштабирования,
 — устойчивость к «ядовитым» сообщениям,
 — необходимость пакетной обработки,
 — требования к порядку сообщений.

Хотя в этой статье основное внимание уделялось Amazon SQS и Apache Kafka, в более широком смысле выбор чаще всего сводится к дилемме между очередью сообщений и потоковой передачей. Однако можно и объединить преимущества обоих подходов.

Стандартизация на одном брокере для публикации событий позволяет сосредоточиться на построении инструментов, системы репликации и наблюдаемости только для одного решения, тем самым снижая издержки на поддержку. Консюмеры же могут направлять сообщения в подходящий брокер для обработки с помощью таких сервисов, как EventBridge, обеспечивая гибкость при сохранении операционной эффективности.


Если ваша работа связана с обработкой больших объемов данных, системами обмена сообщениями или оптимизацией микросервисов, вам наверняка будет полезно углубить знания в этих областях. Рекомендуем обратить внимание на открытые уроки, которые помогут вам освоить ключевые инструменты для работы с потоками данных, интеграциями и фоновыми задачами:

Все открытые уроки по программированию, работе с данными и микросервисам смотрите в календаре мероприятий.

Теги:
Хабы:
+7
Комментарии3

Публикации

Информация

Сайт
otus.ru
Дата регистрации
Дата основания
Численность
101–200 человек
Местоположение
Россия
Представитель
OTUS

Истории