RabbitMQ basic.get and confirmation
I am calling:
GetResponse response = channel.basicGet("some.queue", false); // no auto-ack
....
channel.basicAck(deliveryTag, ...);
However, when I call basicGet
, the messages in the queue remain in Ready and not Unacknowledged. I want them to be unacknowledged so that I can either basic.ack
them (discarding them from the queue) or basic.nack
them
source to share
When executed ack
right after, get
it works great. However, in my case, they were separated by a query. The spring pattern closes the pipe and connection on every execution. Thus, there are three options:
- keep one channel and connection open throughout the life of the application.
- have some kind of conversation area (or worst case: use session) to keep the same channel and reuse it.
- use one channel for inquiry, acknowledge receipt immediately and store messages in memory.
In the previous two cases, you cannot do it with spring RabbitTemplate
source to share
I do the following to mimic Delay ack :
Consumption time
- Get (destroy) a message from the initial queue.
- Create a queue PendingAck_123456.
123456 is a unique message identifier.
Set the following properties:- x-message-ttl (after a Timeout request)
- x-expires (to make sure the temporary queue is removed)
- x-dead-letter-exchange and x-deal-letter-routing-key to request the start queue when TTL expires .
- Post message Pending response to this queue "PendingAck_123456"
- Enter a message to remove it from the initial queue
At the moment of confirmation
- Calculate queue name from message id and get "PendingAck_123456" from queue
- Confirm it (no need to call
.getBody()
).
This will remove it from this pending queue, preventing the TTL from requesting it
Notes
- A queue for only 1 message .. Is it a problem if there are many such queues?
- The requested message will be sent from the input side of the queue .. not the output to the queue (as in a real situation) .. Impact on the order of messages.
- The message is copied by the application to the waiting queue. This is an additional step that can affect overall performance.
- To emulate Nack / Reject, you can copy the message to the Start queue and Ack from the PendingAck queue. The default TTL will do this (later).
source to share