Вопрос или проблема
Мы обновляемся с rabbitmq 3.9 до RabbitMQ 4.0.5 и Erlang 26.2.5.7 на Ubuntu 22, работающем на AWS EC2 i3 экземпляре с 1 x 950 NVMe SSD. Директория mnesia находится на NVMe SSD.
жесткий и мягкий ulimit: 65000
Наша настройка включает 400 классических очередей, и мы наблюдаем неожиданное поведение при обработке постоянных сообщений:
- Постоянные сообщения быстро удаляются с диска при публикации в одну очередь.
- Однако при публикации в несколько очередей, постоянные сообщения остаются на диске значительно дольше, прежде чем быть удаленными.
Это медленное освобождение дискового пространства происходит только при публикации в несколько очередей одновременно.
Любая помощь будет оценена.
Ответ или решение
Для решения проблемы с долгим освобождением дискового пространства при работе с RabbitMQ, необходимо сначала рассмотреть теоретические аспекты, которые могут влиять на поведение системы при обработке постоянных сообщений (persistent messages). Затем приведем примеры возможных причин и решений, а в заключение предложим конкретные шаги для применения на практике.
Теория
RabbitMQ — это система обмена сообщениями, в которой сообщения могут быть помечены как постоянные для обеспечения их сохранности на случай отключения или сбоя сервера. Постоянные сообщения сохраняются на диске, что дает гарантию сохранности, однако, это также приводит к более высокой нагрузке на дисковую подсистему.
При работе с несколькими очередями, такие факторы, как параллелизм, входящая скорость сообщений, и внутренние механизмы управления потоком, могут существенно влиять на производительность. RabbitMQ использует журнал транзакций (transaction log) для хранения постоянных сообщений, и эффективность работы с ним зависит от используемых настроек и архитектуры дисковой подсистемы.
Одним из ключевых моментов, является алгоритм управления памятью и кеширование, которые могут по-разному вести себя при публикующих операциях на нескольких очередях, поскольку это может потребовать более сложной координации и синхронизации между потоками.
Примеры
-
Операции чтения и записи на диск. При публикации сообщений в одну очередь может быть задействован линейный доступ к данным, что ускоряет чтение и запись. Однако, параллельное обращение к нескольким очередям часто приводит к произвольному доступу к файлам, что может замедлить операции ввиду физической фрагментации и увеличенной нагрузки на операционную систему по управлению этими доступами.
-
Кэширование и буферизация. Версии RabbitMQ могут иметь различия в реализации кэширования, что особенно заметно при изменении версий или переходе на более новый бэкенд для хранения сообщений, например, новое поведение может быть распознано как "очистка кэша", которое происходит менее эффективно.
-
Журнал транзакций (transaction log). При интенсификации работы с несколькими очередями может наблюдаться "бутылочное горлышко" в управлении журналом транзакций, так как параллельные изменения данных увеличивают время на обработку и подтверждение транзакций. Это может привести к задержке в том, как быстро журнал освобождает записи, что в свою очередь замедлит освобождение дискового пространства.
Применение
Для эффективного решения проблемы рекомендую предпринять следующие шаги:
-
Мониторинг и анализ. Используйте расширенные метрики для анализа потребления ресурсов при публикации сообщений в RabbitMQ. Инструменты вроде Grafana могут помочь визуализировать и понять, какие именно процессы занимают наибольшее время/ресурс.
-
Настройка RabbitMQ и системы. Проверьте конфигурации RabbitMQ, такие как
disk_free_limit
,vm_memory_high_watermark
, чтобы убедиться, что они соответствуют вашей рабочей нагрузке. Убедитесь, что выланированиеflow control
настроено правильно для предотвращения переполнения очередей. -
Оптимизация дисковой подсистемы. Убедитесь, что NVMe SSD настроен оптимально для рабочих нагрузок высокого уровня случайных операций, включите триммирование диска и проверьте, нет ли потенциальных проблем с ним.
-
Модернизация или переоценка архитектуры RabbitMQ. Рассмотрите возможность использования кластеризации, которая может улучшить распределение нагрузки между несколькими узлами. Также подумайте об изменении архитектуры использования очередей, если это возможно.
-
Логгирование и трассировка. Включите расширенное логгирование и трассировку RabbitMQ для понимания того, где происходят задержки.
-
Проведение тестов. На тестовой среде попробуйте воспроизвести ситуацию и протестировать разные сценарии и конфигурации.
Решение данной проблемы требует комплексного анализа и подхода с учетом как аппаратных, так и программных аспектов. Настоятельно рекомендуется продумать план пошаговой диагностики и оптимизации, основанный на полученных аналитических данных.
Чтобы максимально использовать приведенные рекомендации, учитывайте последние обновления и документацию RabbitMQ совместно с текущими характеристиками используемого оборудования и ПО. Это поможет поддерживать высокий уровень производительности и устойчивости в условиях высоких нагрузок на дисковую и системную подсистемы.