如果没有做客户确认会怎么样?

时间:2013-03-06 09:54:33

标签: java jms hornetq

我有:

  • 一个hornetq-2.2.14-final独立服务器
  • 向队列A发送消息的客户端应用程序C1
  • 使用来自队列A的消息的客户端应用程序C2

C1使用jmstemplate在CLIENT_ACKNOWLEDGE模式下发送消息:

<bean name="jmsTemplate" class="org.springframework.jms.core.JmsTemplate">
    <property name="connectionFactory" ref="connectionFactory" />
    <property name="sessionAcknowledgeModeName" value="CLIENT_ACKNOWLEDGE" />
    <property name="sessionTransacted" value="true" />
</bean>

所以C2应该手动确认消息:

@Override
@Transactional
public void onMessage(Message message) 
{
    try 
    {
        messageHandlerService.handleReceivedMessage(message);
        message.acknowledge();
    } 
    catch (DeserializeXmlException e) 
    {
        // TODO log
        e.printStackTrace();
    }   
    catch (InvalidMessageException e) 
    {
        //TODO log
        e.printStackTrace();
    }
    catch (JMSException e) 
    {
        //TODO log
        e.printStackTrace();
    }   
}

我的问题:

  • 当客户C2收到该消息但在确认之前崩溃时,消息会发生什么?
  • 有没有超时机制?如果是,确认的默认超时是多少?我怎么修改它?

1 个答案:

答案 0 :(得分:5)

当客户关闭或回滚时,任何非确认消息都将被发送回队列。

如果服务器崩溃,如果该消息是非持久性的,则该消息将被重新传递,就像没有发生任何事情一样。

请注意,系统可能会在您调用ack时但在ack实际到达服务器之前崩溃。

通过更改连接工厂上的callTimeout来配置确认超时。

请注意,如果您有两个要更新的资源,并且希望保证ack和数据库插入之间的单个提交(或者您接下来要做的任何事情),那么您需要执行XA事务以保证两个分支都将被提交

崩溃后将重新发送该消息。如果您需要100%保证收据,则需要XA。