今天应用Spring JMS整合ActiveMQ时发现了这样一个问题,搞了几个小时的时间,终于是明白了,随手记录一下,也给用到的朋友一个参考。
关于Spring JMS和ActiveMQ的用法在这里就不说了,推荐一篇文章,对快速的理解很有帮助
http://blog.csdn.net/buyaore_wo/article/details/7093589
好了,进入正题。我们知道,对于向Queue发送消息,如果没有消费者在监听,会将消息持久化,接收jms消息时可以是事务性的和非事务性的。对于事务性的接收,当成功提交之后才会发送确认接收回执无论是receive同步接收还是onMessage这样的异步接收,对于非事务性的接收要根据createSession时定义的标识方式进行确认签收默认是AUTO_ACKNOWLEDGE也就是在onMessage方法成功返回后即确认签收。
比如现在有这样一个需求的场景,我们希望向Queue中发送消息,发送时消费者不在线,当消费者非事务性的连接后,可以接收到它离线时没有接收到的消息。应用Spring的jmsTelement发送消息,用DefaultMessageListenerContainer监听Queue时发现,即使在监听器的onMessage()中抛出异常消息仍然被成功的签收了。消费者再次连接......还是没有消息过来,怎么办呢?看源码吧。
原来是这样啊......DefaultMessageListenerContainer其实是是用轮询的方式,调用session.receive()接收消息,然后再回调注入的监听器的onMessage(),而在非事务性接收的情况下,receive之后就会发送确认签收的回执,已经持久化的消息随即消失,所以在onMessage()中,无论怎么折腾,其实都是对已成功签收的Message进行的操作,怪不得。
既然这样,那把DefaultMessageListenerContainer的sessionTransacted改为true,并且同样在onMessage()中抛出个异常试试,理论上抛出异常后应该回滚了,而且消息会被持久化,结果呢......和理论一样,原因呢......上边已经说了。
好了,汇报完毕,请指示。
分享到:
相关推荐
Spring集成ActiveMQ配置
Spring和ActiveMQ整合的完整实例
Spring整合ActiveMQ实现队列和主题发布订阅通信、一个完整的DEMO
spring整合activemq的maven工程 activemq+spring+maven project
源码为web工程,整合了Spring,SpringMVC、ActiveMQ,启动后,index页面输入消息,控制台输出消息。
Spring整合activemq。。。。。。。。。。。。。。。。。。。。
spring集成activemq例子demo
博客http://blog.csdn.net/poorCoder_/article/details/61192791的代码。Spring整合ActiveMQ的简单实例
Spring集成ActiveMQ配置
百度spring整合activemq 发现几乎都只是在xml文件配置固定的消息队列而且太麻烦。并没有根据需求进行动态生成主题和队列。本文档参考了纯粹的activemq java代码和百度上的demo,很简洁的实现了动态消息队列的生成和...
spring集成ActiveMQ的配置过程
结合博客提供spring+activeMQ的demo源码
ActiveMQ与Spring整合之异步发送邮件。
spring 与ACTIVEMQ整合.
Spring整合ActiveMQ实现点对点与主题发布订阅通信的一个DEMO
支持持久化的采用Spring整合activeMQ与quartz的JMS数据同步实例,包含依赖的jar包
springboot集成activemq实现消息接收demo