ActiveMQ的消息重發與死信管理(DLQ)

DLQ-死信隊列(Dead Letter Queue)用來保存處理失敗或者過期的消息。

出現以下情況時,消息會被redelivered

  1. A transacted session is used and rollback() is called.
  2. A transacted session is closed before commit is called.
  3. A session is using CLIENT_ACKNOWLEDGE and Session.recover() is called.

當一個消息被redelivered超過maximumRedeliveries(缺省爲6次,具體設置請參考後面的鏈接)次數時,會給broker發送一個"Poison ack",這個消息被認爲是a poison pill,這時broker會將這個消息發送到DLQ,以便後續處理。

 

缺省的死信隊列是ActiveMQ.DLQ,如果沒有特別指定,死信都會被髮送到這個隊列。

 

缺省持久消息過期,會被送到DLQ,非持久消息不會送到DLQ

 

可以通過配置文件(activemq.xml)來調整死信發送策略。

 

1.  不使用缺省的死信隊列

        缺省所有隊列的死信消息都被髮送到同一個缺省死信隊列,不便於管理。可以通過individualDeadLetterStrategy或sharedDeadLetterStrategy策略來進行修改。如下:
<broker...>
  <destinationPolicy>
    <policyMap>
      <policyEntries>
        <!— 設置所有隊列,使用 '>' ,否則用隊列名稱 -->
        <policyEntry queue=">">
          <deadLetterStrategy>
            <!--
                    queuePrefix:設置死信隊列前綴
                    useQueueForQueueMessages: 設置使用隊列保存死信,還可以設置useQueueForTopicMessages,使用Topic來保存死信
            -->
            <individualDeadLetterStrategy   queuePrefix="DLQ." useQueueForQueueMessages="true" />
          </deadLetterStrategy>
        </policyEntry>
      </policyEntries>
    </policyMap>
  </destinationPolicy>
  ...
</broker>
 

 

2.  非持久消息保存到死信隊列

       <policyEntry queue=">">
         <deadLetterStrategy>
           <sharedDeadLetterStrategy processNonPersistent="true" />
         </deadLetterStrategy>
       </policyEntry>

 

3.  過期消息不保存到死信隊列

       <policyEntry queue=">">
         <deadLetterStrategy>
           <sharedDeadLetterStrategy processExpired="false" />
         </deadLetterStrategy>
       </policyEntry>

 

4.  持久消息不保存到死信隊列

       對於過期的,可以通過processExpired屬性來控制,對於redelivered的失敗的消息,需要通過插件來實現如下:
丟棄所有死信
<beans>
  <broker ...>
    <plugins>
      <discardingDLQBrokerPlugin dropAll="true" dropTemporaryTopics="true" dropTemporaryQueues="true" />
    </plugins>
  </broker>
</beans>
丟棄指定目的死信
<beans>
  <broker ...>
    <plugins>
      <discardingDLQBrokerPlugin dropOnly="MY.EXAMPLE.TOPIC.29 MY.EXAMPLE.QUEUE.87" reportInterval="1000" />
    </plugins>
  </broker>
</beans>
注意,目的名稱使用空格分隔
The reportInterval property is used to denote how frequently do we output how many messages we have dropped - use 0 to disable.
用正則表達式過濾丟棄消息:
<beans>
  <broker ...>
    <plugins>
      <discardingDLQBrokerPlugin dropOnly="MY.EXAMPLE.TOPIC.[0-9]{3} MY.EXAMPLE.QUEUE.[0-9]{3}" reportInterval="3000" />
    </plugins>
  </broker>
</beans>
Notice that the destination names use regular expressions. These match the number 000..999 at the end of each destination name.

 

5.  死信隊列消息的屬性

死信隊列中的消息,會增加幾個屬性,比如原過期時間(originalExpiration),原originalDeliveryMode等

 

 

參考:

DLQ處理說明:

http://activemq.apache.org/message-redelivery-and-dlq-handling.html

individualDeadLetterStrategy屬性說明:

http://fusesource.com/docs/broker/5.3/configref/http.activemq.apache.or/element/individualdeadletterstr.html

sharedDeadLetterStrategy屬性說明:

http://fusesource.com/docs/broker/5.3/configref/http.activemq.apache.or/element/shareddeadletterstrateg.html

redelivery屬性說明:

http://activemq.apache.org/redelivery-policy.html

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章