TLFox wrote:


Robert Greig wrote:
In a similar vein, it's asynchronous.



Ok sorry to be a pain. But there's also an issue with doing acknowledgements
asynchronously and JMS compliance.

I raised the same issue recently with ActiveMQ which suffers from the same
problem:
http://www.nabble.com/Asynchronous-acknowledgements---are-they-correct--to17277656s2354.html

To summarise, if you send acks async it's not possible to support JMS
AUTO_ACKNOWLEDGE semantics properly. AUTO_ACKNOWLEDGE requires "at most
once" delivery guarantee. This means its ok to lose a message on failure but
you'll never get duplicates.

In order to guarantee "at most once", basically you need to ack the message
synchronously to the server before you give the message to the client via a
receive() call.

If you do that, there's a possibility of lost message if the client fails
after the ack is processed but before the receive() call returns, but
there's no possibility of the message getting delivered more than once after
falure (since it's always acked before receipt).

However if you send the ack async, then the message can actually get acked
*after* it's been giving to the user. Thus introducing a window during which
if failure occurs the message can get redelivered in contravention of JMS
spec.

The JMS spec isn't fully consistent on this point. It clearly states that with AUTO_ACKNOWLEDGE acks are sent *after* the message listener is invoked, so (with listeners at least) this window will always exist even if you sync the acks.

With receive() of course the ack happens before the application sees the message, so you could avoid the window by syncing there, however I don't know offhand of anything that directly states that should be the case.

For CLIENT_ACKNOWLEDGE I agree that strictly speaking you should sync the acks.

--Rafael

Reply via email to