Я использую Spring JMS с очередью / темой TIBCO EMS для своего приложения весенней загрузки. Очередь TIBCO EMS настраивается с помощью EXPLICIT_CLIENT_DUPS_OK_ACKNOWLEDGE. В моем коде я не устанавливаю режим подтверждения, поэтому предполагаю, что spring примет значение AUTO_ACKNOWLEDGE по умолчанию. Поведение, которое я замечаю в моем методе прослушивателя onMessage, заключается в том, что если приложение успешно обрабатывает сообщение, повторная доставка того же сообщения отсутствует. А если приложение генерирует исключение RuntimeException, происходит повторная доставка того же сообщения. Код также имеет для setSessionTranshibited значение true с помощью DefaultJmsListenerContainerFactory. В этом сценарии пружина действительно подтверждает сообщение от моего имени или код должен установить message.acknowledge ().
Поведение подтверждения Spring JMS с TIBCO EMS EXPLICIT_CLIENT_DUPS_OK_ACKNOWLEDGE
Ответы (1)
См. Javadocs для Session
. Auto
означает, что библиотека поставщика автоматически подтверждает сообщение, когда consumer.receive()
возвращает его или consumer.messsageListener()
завершает работу.
С SimpleMessageListenerContainer
ваш слушатель вызывается непосредственно Consumer провайдера, поэтому сообщения не будут автоматически подтверждаться, пока ваш слушатель не завершит нормальный выход.
Вместо этого DirectMessageListenerContainer
вызывает receive()
и вызывает вашего слушателя в своем собственном потоке. Следовательно, нам нужны транзакции для отката подтверждения после возникновения исключения.
person
Gary Russell
schedule
01.02.2021
Я использую DefaultMessageListenerContainer. В javadoc я вижу, что это упомянуто ниже. Обратите внимание, что для режима AUTO_ACKNOWLEDGE по умолчанию этот контейнер применяет автоматическое подтверждение сообщения перед выполнением слушателя без повторной доставки в случае исключения. Но поведение, которое я наблюдаю, как я уже упоминал в вопросе, отличается от того, что указано в javadoc
- person Albin; 01.02.2021
Непонятно, что вы имеете в виду; в вашем вопросе вы сказали, что используете DMLC и
setSessionTransacted=true
; это вызовет повторную доставку, если слушатель выдаст исключение (как вы говорите, это происходит). Сообщение подтверждается внутри транзакции, и транзакция откатывается, следовательно, подтверждение также откатывается, и сообщение повторно ставится в очередь.
- person Gary Russell; 01.02.2021
то, что я говорил, это то, что javadoc сообщает, что контейнер применяет автоматическое подтверждение сообщения «до» выполнения слушателя, но для меня поведение после выполнения. То же, что вы сказали, но javadoc сообщает, что это было раньше. Вот в чем мое замешательство
- person Albin; 05.02.2021
Документ правильный; сообщение действительно подтверждается перед вызовом слушателя (до возврата
receive()
). Просто из-за того, что слушатель выдает исключение, транзакция откатывается (включая уже отправленное подтверждение), поэтому сообщение повторно ставится в очередь. Если вы не используете транзакции, сообщение будет потеряно.
- person Gary Russell; 05.02.2021