Добавить в корзинуПозвонить
Найти в Дзене

Введение в тему: RabbitMQ

I. Что такое RabbitMQ RabbitMQ – распределенная система управления очередью сообщений (message queue). Распределенная, потому что обычно работает как кластер узлов (node-cluster), где очереди распределяются по узлам для обеспечения высокой доступности (high availability) и отказоустойчивости (fault tolerance). Основная цель данного инструмента – принимать и отдавать сообщения. Его можно представить, как почтовое отделение: когда Вы бросаете письмо в ящик, то уверены, что рано или поздно почтальон доставит его по адресу. В этой аналогии RabbitMQ является одновременно и почтовым ящиком, и почтовым отделением, и почтальоном. Наибольшее отличие от почтового отделения в том, что RabbitMQ не имеет дело с бумажными конвертами, а принимает, хранит и отдает бинарные данные – сообщения. В RabbitMQ применяется push-модель: это помогает предотвратить перегрузку пользователей через ограничение предварительной выборки, настроенное консьюмером или потребителем (consumer). По умолчанию в RabbitMQ испо
Оглавление

I. Что такое RabbitMQ

RabbitMQ – распределенная система управления очередью сообщений (message queue). Распределенная, потому что обычно работает как кластер узлов (node-cluster), где очереди распределяются по узлам для обеспечения высокой доступности (high availability) и отказоустойчивости (fault tolerance).

Основная цель данного инструмента – принимать и отдавать сообщения. Его можно представить, как почтовое отделение: когда Вы бросаете письмо в ящик, то уверены, что рано или поздно почтальон доставит его по адресу. В этой аналогии RabbitMQ является одновременно и почтовым ящиком, и почтовым отделением, и почтальоном.

Наибольшее отличие от почтового отделения в том, что RabbitMQ не имеет дело с бумажными конвертами, а принимает, хранит и отдает бинарные данные – сообщения.

В RabbitMQ применяется push-модель: это помогает предотвратить перегрузку пользователей через ограничение предварительной выборки, настроенное консьюмером или потребителем (consumer).

По умолчанию в RabbitMQ используется протокол AMQP 0.9.1, также существуют расширения для поддержки дополнительных протоколов: AMQP 1.0, HTTP, STOMP и MQTT.

II. Протокол AMQP

AMQP (Advanced Message Queuing Protocol) — открытый протокол для передачи сообщений между компонентами системы. Основная идея состоит в том, что отдельные подсистемы (или независимые приложения) могут обмениваться произвольным образом сообщениями через AMQP-брокер, который осуществляет маршрутизацию (routing), возможно гарантирует доставку, распределение потоков данных (dataflow), подписку на нужные типы сообщений.

AMQP работает с пятью сущностями:

producer – отправитель сообщения или издатель;

message – само сообщение;

exchange (обменник или точка обмена) – в него отправляются сообщения; обменник распределяет сообщение в одну или несколько очередей, маршрутизирует сообщения в очередь на основе созданных связей (binding*) между ним и очередью;


binding (привязка) — правило, которое сообщает точке обмена в какую из очередей эти сообщения должны попадать; обменник и очередь могут быть связаны несколькими привязками

queue (очередь) – структура данных на диске или в оперативной памяти, которая хранит ссылки на сообщения и отдает копии сообщений потребителям (одна очередь может использоваться несколькими потребителями);

consumer – исполнитель или потребитель, который из этой очереди что-то заберёт и что-то сделает.

III. Обмен сообщениями в RabbitMQ

Основная идея модели обмена сообщениями в RabbitMQ (см. рис. 1) заключается в том, что producer (издатель) не отправляет сообщения непосредственно в очередь. На самом деле и довольно часто издатель даже не знает, будет ли сообщение вообще доставлено в какую-либо очередь.

Вместо этого издатель может отправлять сообщения только на обменник. С одной стороны, обменник получает сообщения от издателей, а с другой – отправляет их в очереди. Обменник должен точно знать, что делать с полученным сообщением. Должно ли оно быть добавлено в определенную очередь? Должно ли оно быть добавлено в несколько очередей? Или сообщение нужно игнорировать.

Рис. 1 – Модель обмена сообщениями в RabbitMQ
Рис. 1 – Модель обмена сообщениями в RabbitMQ

Кратко работу RabbitMQ можно описать следующим образом:

1) издатель отправляет сообщение определенному обменнику;

2) обменник, получив сообщение, маршрутизирует его в одну или несколько очередей в соответствии с правилами привязки между ним и очередью;

3) очередь хранит ссылку на это сообщение, само сообщение хранится в оперативной памяти или на диске;

4) как только потребитель готов получить сообщение из очереди, сервер создает копию сообщения по ссылке и отправляет;

5) потребитель получает сообщение и отправляет брокеру подтверждение;

6) брокер, получив подтверждение, удаляет копию сообщения из очереди, затем удаляет из оперативной памяти и с диска.

Существует несколько видов точек обмена (см. рис. 1):

fanout exchange – все сообщения доставляются во все очереди, даже если в сообщении задан ключ маршрутизации;

direct exchange – используется, когда нужно доставить сообщение в определенные очереди; сообщение публикуется в обменник с определенным ключом маршрутизации и попадает во все очереди, которые связаны с этим обменником аналогичным ключом маршрутизации (routing key) – строкой; поиск соответствия происходит при помощи проверки строк на эквивалентность;

topic exchange – аналогично direct exchange дает возможность осуществления выборочной маршрутизации путем сравнения ключа маршрутизации, но, в данном случае, ключ задается по шаблону; при создании шаблона используются 0 или более слов (буквы AZ и az и цифры 0-9), разделенных точкой, а также символы * и #;

headers exchange – позволяет добавлять к сообщениям заголовки получателей; каждая привязка включает в себя точное соответствие значений заголовка, к привязке можно добавить несколько значений с любыми или всеми значениями, необходимыми для соответствия.

Какие фишки подразумеваются в очереди и уже реализованы в RabbitMQ:

1. Durable – возможность сохранения состояния при перезагрузке сервера. Например, сервер «уронили» (или он «упал» сам), а очередь нужно не потерять. Для скорости работы очередь хранится в RAM (Random Access Memory, память с произвольным доступом), поэтому, чтобы обеспечить её персистентное состояние, нужно дополнительно сохранять очередь куда-то на диск. Для этого делается дамп, сохраняется на диске, в случае «падения» поднимается дамп с диска.

2. TTL (time to live) & expiration – можно указать каждому сообщению или всем сообщениям в очереди (очереди целиком), сколько они будут жить. Например, поступает заказ. Мы понимаем, что через 60 минут он уже станет неактуальным (например, биржа – через час уже значительно изменятся ставки; или шаурма – ни один клиент не будет ждать шаурму час), и мы можем задать TTL, чтобы каждое сообщение, которое пролежит больше 60 минут, исчезало из очереди.

3. ACK (acknowledge) – cообщения могут быть нескольких видов, и самые популярные из них:

• сообщение, которое нужно сразу удалить из очереди, как только оно было взято, не дожидаясь ответа от того, кто его забрал (это и есть ACK);

• сообщение, которое не нужно удалять из очереди, пока не получен нужный ответ. Это сообщение мы помечаем и блокируем, чтобы другие не взяли его. Если нам не вернётся ответ, оно останется у нас, и другие исполнители смогут взять его.

4. Dead lettering – отправленное сообщение вернулось с ошибкой (блек-джеком) в очередь и нам нужно обработать его не сразу, а с задержкой 5–10 секунд. Такое часто бывает, когда провайдер данных не доступен (т. е. провайдер возвращает нам ошибку, скажем, 404, 504 или что-то подобное). В этом нет ничего страшного, нужно вернуть сообщение в очередь и при возврате указать, через какое время этот элемент будет доступен для повторного просмотра.

IV. Для чего используется RabbitMQ?

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

RabbitMQ идеально подходит для веб-серверов, которым требуется быстрый запрос-ответ.

Этот инструмент распределяет нагрузку между рабочими приложениями при высокой нагрузке (более 20 000 сообщений в секунду) и может обрабатывать фоновые задания или длительные задачи, такие как преобразование PDF, сканирование файлов или масштабирование изображений.

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

Источники:

1) Веб-сайт: https://habr.com/ru/company/itsumma/blog/416629/

2) Веб-сайт: https://habr.com/ru/post/149694/

3) Веб-сайт: https://habr.com/ru/post/488654/

4) Веб-сайт: https://habr.com/ru/post/489086/

5) Веб-сайт: https://kt-team.ru/hr/blog/rabbitmq#rabbit

Автор: Александра Поверина, IT-переводчик

Материал подготовлен для телеграм-канала по ИТ-переводу @alliancepro