一个 JDBC 事务是不够的:如果你读过一条消息,数据库操作失败,tomcat 被关闭,消息就丢失了。
如果每条消息都会触发数据库中的插入/更新,您可以使用CLIENT_ACKNOWLEDGE 模式:
final boolean transacted = false;
final int ackMode = Session.CLIENT_ACKNOWLEDGE;
final QueueSession queueSession = queueConnection.createQueueSession(
transacted, ackMode);
这样您就可以阅读消息并更新数据库。如果数据库更新成功,您可以使用
确认消息
message.acknowledge();
没有acknowledge,消息将被重新传递:所以重启tomcat后,你的消息监听器应该会再次看到消息。您可以使用queueSession.recover() 以编程方式重新启动交付。
由于tomcat 可能在成功的数据库更新和确认之间关闭,您应该确保正确处理重复消息。
一种变体是使用事务处理的会话:
final boolean transacted = true;
// 2nd parameter is ignored if the session is transacted
final QueueSession queueSession = queueConnection.createQueueSession(
transacted, -1);
在这种模式下,您可以使用一次提交确认多条消息:
queueSession.commit();
如果多条消息导致单个数据库操作,则需要此模式(您必须收集一些消息,然后才能更新数据库)。