ActiveMQ中如何实现消息的重试和死信队列?

ActiveMQ 中可以通过以下方式实现消息的重试和死信队列:
1、 消息重试:

  • 发送端设置消息重发次数和重发间隔:
<broker>
  <destinationPolicy>
    <policyEntry topic=">"> 
      <pendingDurableSubscriberPolicy>
        <redeliveryDelay>5000</redeliveryDelay>  <!-- 重发间隔5s -->
        <maximumRedeliveries>3</maximumRedeliveries>  <!-- 最大重发3次 -->
      </pendingDurableSubscriberPolicy>
    </policyEntry>    
  </destinationPolicy>
</broker>
  • 消费端使用事务消费,消费失败则回滚事务实现重试:
Session session = connection.createSession(true, Session.SESSION_TRANSACTED);  
MessageConsumer consumer = session.createConsumer(queue);

Message message = consumer.receive();
try {  
  // 消息消费逻辑
  session.commit();  
} catch (Exception e) {
  session.rollback(); // 消费失败,回滚事务,消息会被重新消费 
}

2、 死信队列:

  • 设置消息最大重发次数,超过此次数消息进入死信队列:
<broker>
  <destinationPolicy>
    <policyEntry topic=">">  
      <pendingDurableSubscriberPolicy>
        <redeliveryDelay>5000</redeliveryDelay>
        <maximumRedeliveries>3</maximumRedeliveries>  
      </pendingDurableSubscriberPolicy>
      <deadLetterStrategy>
        <deadLetterQueue physicalName="DLQ" maximumRedeliveries="3"/>  
      </deadLetterStrategy> 
    </policyEntry>     
  </destinationPolicy>
</broker>
  • 消息在超过最大重发次数后会进入 DLQ 死信队列。
  • 消费端也可以将消息拒收进入死信队列:
MessageConsumer consumer = session.createConsumer(queue);
Message message = consumer.receive();
message.setJMSRedelivered(true);  // 将消息标记为已重发 
message.acknowledge();          // 拒收消息