基于this教程,我正在使用@EnableJms和@JmsListener批注在我的应用程序中注册队列侦听器。我正在连接到IBM MQ,正在使用jndi建立连接工厂。我已经阅读了有关确认模式等的信息,但这对我来说仍然是新事物。我的问题是消息没有返回到队列中(永远不会再次调用侦听器)。
@Bean
public DefaultJmsListenerContainerFactory jmsListenerContainerFactory() {
DefaultJmsListenerContainerFactory factory
= new DefaultJmsListenerContainerFactory();
factory.setConnectionFactory(connectionFactory());
factory.setSessionTransacted(true);
factory.setSessionAcknowledgeMode(Session.AUTO_ACKNOWLEDGE); //I have tried also CLIENT_ACKNOWLEDGE
return factory;
}
@JmsListener(containerFactory = "jmsListenerContainerFactory", destination = "myQueue")
@SendTo("secondQueue")
public String testListener(String message){
if(true) throw new NullPointerException();
else return message;
}
任何帮助将不胜感激。 我还有第二个问题。据我了解,如果我想对数据库执行任何操作,回滚提交的唯一方法(如果此后出现问题)将是创建事务管理器?如果没有,我将需要检测重复的消息。
答案 0 :(得分:1)
首先将确认模式设置为Session.CLIENT_ACKNOWLEDGE
并且在接收到消息时,如果处理正确,则只需调用message.acknowledge()
方法,否则就不调用。
它将自动保留在队列中,您无需重新发送。
您需要使用
import javax.jms.Message
答案 1 :(得分:0)
我创建了简单的Spring Boot应用程序和IBM MQ的Docker容器来测试您的情况。 我在本教程中找到了很好的说明:https://developer.ibm.com/tutorials/mq-jms-application-development-with-spring-boot/
在您的情况下,此环境的行为符合预期:接收消息的无尽循环-> NullPointerException->返回消息-> ...
除了我发现IBM MQ的名为“回退队列和阈值”的功能外,您还会在此博客文章中找到解释:https://community.ibm.com/community/user/imwuc/browse/blogs/blogviewer?BlogKey=28814801-083d-4c80-be5f-90aaaf81cdfb
简而言之,可以限制消息在异常后返回队列的次数,并在此限制之后将消息发送到另一个队列。
在您的情况下,此功能可能会在目标队列中使用。