Как гарантировать надежную доставку JMS
Я думаю, что множество (Весна в моем случае) приложений, использующих JMS, могут следовать этому рабочему процессу:
Database A ===> Producer ===> JMS Queue ===> Consumer ===> Database B
тогда надежность является проблемой. Скажем, если при записи данных в Database A
всегда должно быть отмечено как delivered
, когда сообщение содержит запись данных действительно потребляется и сохранения данных в Database B
. Тогда возникают вопросы:
насколько мне известно, в настоящее время протокол JMS не определяет никаких функций для отправки подтверждения из
consumer
доproducer
, но толькоMOM
, поэтому фактическийconsumer-to-producer
методы подтверждения различаются поставщиком JMS. Значит ли это, что нет способа разработать механизм для такого подтверждения, который может работать для всех продуктов JMS(ActiveMQ, WebSphere MQ и Jboss MQ)?рассмотрим сценарий затемнения, то делает ли он сообщения в очереди просто испариться так нужно повторно отправить? или различные продукты JMS могут забрать то, что осталось, так как сообщения Сериализовано, чтобы отсутствующее сообщение могло быть вызвано только управлением транзакциями или конфигурацией async/sync, но не из-за сервера приложений?
3 ответов
JMS гарантирует доставку сообщения по природе, если сообщение опубликовано, то оно будет доставлено потребителю, если есть один, что бы ни случилось, мама предназначена для обеспечения этого факта. В любом случае, доставлено не обязательно означает обработано.
надежность обеспечена различным механизмом:
- первый-это сохранение сообщения в очереди (очередь и сообщение должны быть помечены как постоянные, что является значением по умолчанию), которое убедитесь, что сообщение не будет потеряно в случае прерывания системы.
- тогда у вас есть подтверждение и политику повтора, сообщение будет оставаться в очереди, пока потребитель признает его и в случае сеанса, будет повторно доставлена до потребителя оперативно обработает сообщение, или максимальная количество попыток достигнуто. Неудачное сообщение может быть перенаправлено в очередь мертвых писем для анализа.
чтобы обеспечить согласованность между двумя источниками данных, вы должны используйте XA транзакции, по крайней мере, на производитель стороне (у вас есть как минимум 2 ресурсов предполагает в транзакции базы данных и JMS) для того, чтобы гарантировать, что сообщение не будет опубликовано на очереди, если фиксация в базе данных произошел сбой, или базы данных не будут обновлены, если сообщение в очереди не. Потребление сообщений также должно быть обработано, чтобы обеспечить повторную доставку в случае отката.
границы транзакций никогда не будут включать как потребителя, так и производителя, потому что это конфликтует с асинхронным характером системы обмена сообщениями, вы не можете позволить себе заблокировать ресурсы на стороне производителя, пока потребитель не обработает сообщение, потому что у вас нет гарантии, когда это произойдет.
NB: в случае, если ваша база данных не поддерживает XA (или для повышения производительности), и если у вас есть только 2 ресурса, подразумеваемые в транзакции (база данных и очередь JMS), вы можете посмотреть на Ведение Журнала Последней Оптимизации Транзакций Ресурсов
1) из моего опыта работы с администраторами очередей (серии MQ, ActiveMQ и HornetQ) мне никогда не требовалось такого подтверждения между производителем/потребителем. Также среда, с которой я имел дело, трафик составлял около 50/60 миллионов объектов в день на несколько очередей. И очереди тоже сохраняются.
2)в моем случае использование механизма сохранения в Администраторе очередей было полностью достаточным для обработки сценария отключения. Я использовал сохранение диска в серии MQ и HornetQ.
однако иногда, чтобы определить количество сообщений, мы разработали некоторые механизмы для сравнения базы данных A с базой данных B, чтобы убедиться, что сообщения также потребляются. Я не знаю, должна ли архитектура JMS предоставлять такой механизм, потому что такая задача может снизить производительность.
Это что - то - с моей точки зрения-что вы должны измерить в своей системной архитектуре, насколько важно соответствовать этой информации, потому что это не так просто держать.
с уважением.
Если я понимаю ваш вопрос, это похоже на случай транзакций JTA/XA (если ваши поставщики DB/JMS поддерживают их). Менеджеры Spring TX могут помочь сделать управление tx (больше) агностиком поставщика.
FYI, я использую Apache Camel для этого типа потока, который имеет довольно хорошую обработку ошибок между производителями/потребителями.