RabbitMQ позволяет взаимодействовать различным программам при помощи протокола AMQP. RabbitMQ является отличным решением для построения SOA (сервис-ориентированной архитектуры) и распределением отложенных ресурсоемких задач.
Под катом перевод первого из шести уроков официального сайта. Примеры на python, но его знание вовсе не обязательно. Аналогичные примеру программы можно воспроизвести практически на любом популярном ЯП. [так выглядят комментарии переводчика, т.е. меня]
- Вступление
- Hello World!
- Отправка сообщений
- Получение сообщений
- Ну а теперь все вместе
- Реализация шины событий с помощью RabbitMQ для среды разработки или тестирования
- Реализация простого метода публикации с помощью RabbitMQ
- Реализация кода подписки с помощью интерфейса API RabbitMQ
- Дополнительные ресурсы
- RabbitMQ: Введение в AMQP
- 🔥 Видео
Вступление
RabbitMQ ‒ это брокер сообщений. Его основная цель ‒ принимать и отдавать сообщения. Его можно представлять себе, как почтовое отделение: когда Вы бросаете письмо в ящик, Вы можете быть уверены, что рано или поздно почтальон доставит его адресату [видимо, автор ни разу не имел дела с Почтой России]. В этой аналогии RabbitMQ является одновременно и почтовым ящиком, и почтовым отделением, и почтальоном.
Наибольшее отличие RabbitMQ от почтового отделения в том, что он не имеет дела с бумажными конвертами ‒ RabbitMQ принимает, хранит и отдает бинарные данные ‒ сообщения.
В RabbitMQ, а также обмене сообщениями в целом, используется следующая терминология:
- Producer (поставщик) ‒ программа, отправляющая сообщения. В схемах он будет представлен кругом с буквой «P»:
- Queue (очередь) ‒ имя «почтового ящика». Она существует внутри RabbitMQ. Хотя сообщения проходят через RabbitMQ и приложения, хранятся они только в очередях. Очередь не имеет ограничений на количество сообщений, она может принять сколь угодно большое их количество ‒ можно считать ее бесконечным буфером. Любое количество поставщиков может отправлять сообщения в одну очередь, также любое количество подписчиков может получать сообщения из одной очереди. В схемах очередь будет обозначена стеком и подписана именем:
Hello World!
Первый пример не будет особо сложным ‒ давайте просто отправим сообщение, примем его и выведем на экран. Для этого нам потребуется две программы: одна будет отправлять сообщения, другая ‒ принимать и выводить их на экран.
Общая схема такова: Поставщик отправляет сообщения в очередь с именем «hello», а подписчик получает сообщения из этой очереди.
Библиотека RabbitMQ
- py-amqplib
- txAMQP
- pika
В примерах будет использована библиотека pika. Ее можно установить при помощи менеджера пакетов pip:
Если отсутствуют pip или git-core, то сначала необходимо установить их:
Для Windows (для установки easy_install необходимо запустить MS Windows Installer для setuptools):
Отправка сообщений
Наша первая программа send.py будет просто отправлять одно сообщение в очередь.
Мы подключились к брокеру сообщений, находящемуся на локальном хосте. Для подключения к брокеру, находящемуся на другой машине, достаточно заменить «localhost» на IP адрес этой машины.
Перед отправкой сообщения мы должны убедиться, что очередь, получающая сообщение, существует. Если отправить сообщение в несуществующую очередь, RabbitMQ его проигнорирует. Давайте создадим очередь, в которую будет отправлено сообщение, назовем ее «hello»:
Теперь все готово для отправки сообщения. Наше первое сообщение будет содержать строку и будет отправлено в очередь с именем «hello».
Вообще, в RabbitMQ сообщения не отправляются непосредственно в очередь, они должны пройти через exchange (точка обмена). Но сейчас мы не будем заострять на этом внимание, точки обмена будут рассмотрены в третьем уроке. Сейчас достаточно знать, что точку обмена по-умолчанию можно определить, указав пустую строку. Это специальная точка обмена ‒ она позволяет определять, в какую именно очередь отправлено сообщение. Имя очереди должно быть определено в параметре routing_key:
Перед выходом из программы необходимо убедиться, что буфер был очищен и сообщение дошло до RabbitMQ. В этом можно быть уверенным, если использовать безопасное закрытие соединения с брокером.
Получение сообщений
Наша вторая программа receive.py будет получать сообщения из очереди и выводить их на экран.
Также как и в первой программе сначала необходимо подключиться к RabbitMQ. Для этого следует использовать тот же код, как и ранее. Следующий шаг, как и прежде ‒ убедиться, что очередь существует. Команда queue_declare не будет создавать новую очередь, если она уже существует, поэтому сколько бы раз не была вызвана эта команда, все-равно будет создана только одна очередь.
Вы можете задаться вопросом, почему мы объявляем очередь снова, ведь она уже была объявлена в первой программе. Это нужно, чтобы быть уверенным в существовании очереди, так будет, если сначала будет запущена программа send.py. Но мы не знаем, какая программа будет запущена раньше. В таких случаях лучше объявить очередь в обеих программах.
Мониторинг очередей
Если Вы хотите посмотреть, какие очереди существуют в RabbitMQ на данный момент, Вы можете сделать это с помощью команды rabbitmqctl (потребуются права суперпользователя):
[в нашей компании используют более удобный скрипт мониторинга:]
[скрипт выводит и обновляет каждые 2 секунды таблицу со списком очередей: имя очереди; количество сообщений в обработке; количество сообщений готовых к обработке; общее количество сообщений; устойчивость очереди к перезагрузке сервиса; является ли временной очередью; количество подписчиков]
Получение сообщений из очереди более сложный процесс, чем отправка. Получение осуществляется при помощи подписки с использованием callback функции. При получении каждого сообщения библиотека Pika вызывает эту callback функцию. В нашем примере она будет выводить на экран текст сообщения.
Далее, нам нужно обозначить, что callback функция будет получать сообщения из очереди с именем «hello»:
Здесь необходимо быть уверенным в том, что очередь, на которую мы хотим подписаться, была объявлена. Мы сделали это ранее с помощью команды queue_declare.
Параметр no_ack будет рассмотрен позже [во втором уроке].
И, наконец, запуск бесконечного процесса, который ожидает сообщения из очереди и вызывает callback функцию, когда это необходимо.
Ну а теперь все вместе
Теперь мы можем попробовать запустить наши программы в терминале. Сначала отправим сообщение при помощи программы send.py:
Выполнение этой программы будет завершаться после отправки каждого сообщения. Теперь сообщение нужно получить:
Отлично! Мы отправили наше первое сообщение через RabbitMQ. Как Вы могли заметить, выполнение программы receive.py не завершилось. Она будет ожидать следующих сообщений, а остановить ее можно, нажав Ctrl+C.
Попробуйте запустить send.py снова в новом окне терминала.
Мы изучили, как отправлять и получать сообщения через именованные очереди. В следующем уроке мы создадим простую очередь задач [ресурсоемких].
UPD: библиотеку, работающую с RabbitMQ, для своего любимого ЯП Вы можете найти на официальном сайте тут.
Видео:Apache Kafka урок 1. Зачем нужна, что это? RabbitMQ vs Kafka vs БДСкачать
Реализация шины событий с помощью RabbitMQ для среды разработки или тестирования
Начать следует с того, что если вы создаете пользовательскую шину событий на основе RabbitMQ в контейнере, как это делается в приложении eShopOnContainers, ее следует использовать только в средах разработки и тестирования. Не применяйте ее в рабочей среде, если только вы не разрабатываете ее в рамках служебной шины, готовой к развертыванию в рабочей среде. Простая пользовательская шина событий может быть лишена многих критически важных для рабочей среды возможностей, которыми обладают коммерческие служебные шины.
Одна из пользовательских реализаций шины событий в eShopOnContainers по сути представляет собой библиотеку, использующую API RabbitMQ. (Существует и еще одна реализация на основе Служебной шины Azure.)
Реализация шины событий с помощью RabbitMQ позволяет микрослужбам подписываться на события, публиковать и принимать их, как показано на рисунке 6–21.
Рис. 6–21. Реализация шины событий на основе RabbitMQ
RabbitMQ выступает в роли посредника между издателем сообщения и подписчиками и обрабатывает распространение. В коде класс EventBusRabbitMQ реализует универсальный интерфейс IEventBus. Для этого применяется внедрение зависимостей, что позволяет переходить от этой версии для разработки и тестирования к рабочей версии.
Реализация образца шины событий для разработки и тестирования на основе RabbitMQ представляет собой стандартный код. Она должна обрабатывать подключение к серверу RabbitMQ и предоставлять код для публикации события сообщения в очередях. Кроме того, должен быть реализован словарь коллекций, содержащий обработчики событий интеграции для каждого типа событий. Для каждого из этих типов событий могут применяться разные способы создания экземпляра и подписки для каждой микрослужбы-получателя, как показано на рисунке 6–21.
Видео:Что такое RabbitMQ и чем он отличается от Apache Kafka за 10 минутСкачать
Реализация простого метода публикации с помощью RabbitMQ
Следующий код является упрощенной версией реализации шины событий для RabbitMQ, демонстрирующей весь сценарий. Вам необязательно обрабатывать подключение таким образом. Чтобы увидеть полную реализацию, просмотрите фактический код в репозитории dotnet-architecture/eShopOnContainers.
Реальный код метода Publish в приложении eShopOnContainers улучшен с помощью политики повтора Polly, которая пытается выполнить задачу повторно несколько раз, если контейнер RabbitMQ не готов. Это может произойти, если контейнеры запускаются с помощью docker-compose. Например, контейнер RabbitMQ может запускаться медленнее других.
Как было сказано ранее, в RabbitMQ возможно множество конфигураций, поэтому этот код следует использовать только в средах разработки и тестирования.
Видео:Основы RabbitMQ: что это и как это работает!Скачать
Реализация кода подписки с помощью интерфейса API RabbitMQ
Так же как и в случае с кодом публикации, приведенный ниже код представляет собой часть упрощенной реализации шины событий для RabbitMQ. Изменять его также обычно не нужно, если его не требуется улучшить.
С каждым типом событий связан канал для получения событий из RabbitMQ. Для каждого канала и типа событий может быть столько обработчиков событий, сколько требуется.
Метод Subscribe принимает объект IIntegrationEventHandler, который похож на метод обратного вызова в текущей микрослужбе, а также связанный с ним объект IntegrationEvent. Затем добавляется обработчик событий в список обработчиков событий, которые может иметь каждый тип событий интеграции в клиентской микрослужбе. Если код клиента еще не подписался на событие, для данного типа событий создается канал, который позволяет получать события из RabbitMQ принудительным образом, когда они публикуются из любой другой службы.
Как упоминалось выше, шина событий, реализованная в eShopOnContainers, предназначена только для образовательных целей, так как она обрабатывает только основные сценарии и не готова к рабочей среде.
Сведения о рабочих сценариях просмотрите в дополнительных ресурсах о RabbitMQ и разделе Реализация связи на основе событий между микрослужбами.
Видео:Брокеры сообщений RabbitMQ, Kafka и Redis в работе системного аналитика: как и когда использоватьСкачать
Дополнительные ресурсы
Готовое к работе решение с поддержкой RabbitMQ.
Видео:БРОКЕР СООБЩЕНИЙ RABBITMQ ДЛЯ САМЫХ МАЛЕНЬКИХ. ВВЕДЕНИЕ.Скачать
RabbitMQ: Введение в AMQP
Построение больших и сложных систем всегда связано с решением проблем обмена данными между различными их узлами. Дополнительные трудности вносят такие факторы, как требования к отказоустойчивости, географическое разнесение подсистем, наличие узлов, взаимодействующих сразу с несколькими другими. Не всегда удобно использовать пресловутую систему клиент-сервер, да и архитектура точка-точка может оказаться не самым подходящим представлением связей.
И вот, в один прекрасный день, собрались инженеры с духом, и разработали AMQP — Advanced Message Queuing Protocol. Этот протокол позволяет не задумываться над тем, где находятся получатели сообщения, сколько их, от кого надо ждать сообщение, когда оно будет доставлено получателю. Кроме этого, AMQP снимает с разработчика ещё многие рутинные задачи и позволяет заниматься непосредственной проблемой, а не обслуживанием процесса разработки.
AMQP имеет три базовых понятия:
- Обменник (exchange)
- Очередь (queue)
- Связь, или маршрут (routing key)
Обмен сообщениями осуществляется в пределах одного обменника (есть ещё цепное связывание, но об этом в другой раз), в котором определены связи, являющиеся своеобразными маршрутами, по которым идут сообщения, попавшие в этот обменник. Каждый маршрут связывает обменник с одной или несколькими очередями. Программное обеспечение, реализующее описанные действия, называют AMQP-сервером. Узлы, помещающие сообщения в обменники и получающие их из очередей, называются AMQP-клиентами. Другими словами, AMQP-сервер предоставляет шину обмена данными, а AMQP-клиенты используют эту шину для обмена сообщениями между собой.
Клиенты могут создавать новые обменники (об их типах поговорим позже) и очереди:
Процесс помещения данных на шину называется публикацией. Когда AMQP-клиент публикует сообщение на шину, он задаёт имя обменника и имя связи:
До этого момента, один из клиентов должен осуществить связку, указав имя обменника, очереди и маршрут, соответствующий ей:
В результате, сообщение будет доставлено в очередь .Но на этом ещё не всё, так как путь сообщения очередью не заканчивается. Один из AMQP-клиентов подписывается на получение сообщений, попавших в заданную очередь:
— идентификатор процесса. Здесь и далее работа с AMQP будет описываться с точки зрения программирования на Erlang, в реализациях клиентов на других языках сообщения вычитываются из очереди явной инструкцией, либо вешаются коллбэки и подписки как таковой нет. После подписки на очередь, все сообщения, попавшие в неё, будут пересылаться подписанному процессу. Если на одну очередьподписано несколько процессов, сообщения будут распределяться по подписчикам методом round-robin.
Для получения ответа, при отправлении запроса в свойствах сообщения заполняется полеReply-To, содержащее, как правило, очередь приватного типа, на которую подписан только отправитель.
На этом пока всё, в следующий раз постараюсь написать про типы обменников и показать примеры кода, хотя посмотреть их можно уже сейчас вот здесь.
🔥 Видео
Брокер сообщений RabbitMQ | Tutorial для начинающих на русском | Урок 3 | Веб интерфейс RabbitMQСкачать
Микросервисы на пальцах. Брокеры, Kafka, RabbitMq, EventSourcing.Скачать
Брокер сообщений RabbitMQ | Tutorial для начинающих на русском | Урок 1 | ВведениеСкачать
Что такое RabbitMQ и чем он отличается от Apache Kafka за 10 минутСкачать
Очереди сообщений с RabbitMQ: что такое, когда нужно, какие проблемы решаетСкачать
Что такое Apache Kafka за 5 минутСкачать
Межсервисное взаимодействие. Очереди сообщенийСкачать
RabbitMQ базовый курс за час. Установка, админ панель. Зачем нужен Rabbit MQ. Брокер сообщенийСкачать
Брокер сообщений RabbitMQ | Tutorial для начинающих | Урок 4 | Обменник: Default Exchange | .Net C#Скачать
Самый простой пример использования Rabbitmq c#Скачать
1С Обмены через брокеры сообщений. RabbitMQ.Скачать
Шины VS брокеры сообщений | KT.Team | Андрей ПутинСкачать
Когда и зачем нужен RabbitMQСкачать
Брокер сообщений RabbitMQ | Tutorial для начинающих на русском | Урок 2 | Установка и настройкаСкачать