[ 
https://issues.apache.org/jira/browse/AMQ-6059?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel
 ]

Nevin Chen updated AMQ-6059:
----------------------------
    Attachment: activemq.xml

> DLQ message lost after broker restarts
> --------------------------------------
>
>                 Key: AMQ-6059
>                 URL: https://issues.apache.org/jira/browse/AMQ-6059
>             Project: ActiveMQ
>          Issue Type: Bug
>          Components: Broker
>    Affects Versions: 5.12.1
>         Environment: Windows, Linux Redhat
>            Reporter: Nevin Chen
>         Attachments: activemq.xml
>
>
> *How to Reproduce*
> 1. Default ActiveMQ 5.12.1 package with the attached activemq.xml.
> 2. Send a message to a queue with expiration time one second.
> 4. After the expiry time, the message will be moved to DLQ. This can be 
> monitored by the AMQ web console.
> 5. Restart AMQ. You will find that the message disappear from the AMQ web 
> console. Try to consume the message from the DLQ, nothing is received.
> *Cause Analysis*
> 1. KahaDB works well. It means the cause should be related to the leveldb 
> mechanism.
> 2. In my understanding, the JMS message is persistent to a log file and 
> leveldb will maintain to a reference to the position where the JMS message is 
> stored in the log. After a message expires, AMQ will copy the expired JMS 
> message and the reference to the posistion is also copied, then send to DLQ. 
> When AMQ restarts, DLQ will recover the message from the persistent storage. 
> Since the DLQ message shares the same reference to the JMS message data, the 
> message in DLQ also has the expiration time that is the same as the original 
> message. The expiry scanner will detect the DLQ message expires and remove 
> it. That's why the message is lost after restart.
> 3. Actually, the message to DLQ is not completely the same as the origial 
> message. Because the expiration time will be reset to 0 and some more message 
> properties will be added. The DLQ message should not reuse the same reference 
> to message data. For more details, please refer to 
> org.apache.activemq.broker.region.RegionBroker.sendToDeadLetterQueue(ConnectionContext
>  context, MessageReference node, Subscription subscription, Throwable 
> poisonCause) method.
> *Fixed Proposal*
> In 
> org.apache.activemq.broker.region.RegionBroker.sendToDeadLetterQueue(ConnectionContext
>  context, MessageReference node, Subscription subscription, Throwable 
> poisonCause) method, after the message is copied, set the dataLocator to null 
> (message.getMessageId().setDataLocator(null) to force leveldb to save the new 
> JMS message data and refer to a new position.



--
This message was sent by Atlassian JIRA
(v6.3.4#6332)

Reply via email to