[rabbitmq-discuss] Explicit ACKs - Timeout Algorithm? (related: Net::Stomp)
Darien Kindlund
darien at kindlund.com
Wed Jan 14 20:28:39 GMT 2009
One of the other questions I had centers around RabbitMQ's method (or
maybe the rabbitmq-stomp connector) of dealing with explicit ACKs.
Using Tony's example perl code (rabbitmq_stomp_recv.pl) as a basis:
1 #!/usr/bin/perl -w
2 # subscribe to messages from the queue 'foo'
3 use Net::Stomp;
4 my $stomp = Net::Stomp->new({hostname=>'localhost', port=>'61613'});
5 $stomp->connect({login=>'guest', passcode=>'guest'});
6 $stomp->subscribe({'destination'=>'foo', 'ack'=>'client'});
7 while (1) {
8 my $frame = $stomp->receive_frame;
9 print $frame->body . "\n";
10 $stomp->ack({frame=>$frame});
11 last if $frame->body eq 'QUIT';
12 }
13 $stomp->disconnect;
Specifically, assume you have two perl clients both running this code
and are both acting as consumers to a shared queue. If one instance
of this code crashes (for whatever reason) after line 8 but before
line 10, then RabbitMQ will do the right thing and redeliver the
(previously acquired?) message to the other instance of the perl code
that is still running.
Now, what if both perl-based consumers were slightly different.
Meaning, one consumer behaves normally (equivalent to
rabbitmq_stomp_recv.pl), but the other consumer is poorly written, and
every once in awhile enters some sort of infinite loop after line 8
but before line 10. Essentially, this consumer has acquired (?) the
message but not explicitly acknowledged the message. In this case,
I'm thinking the "right thing" would be for RabbitMQ to create some
sort of timeout, where after X minutes(?), if the message doesn't get
acknowledged, then RabbitMQ will alter the message to be "not
acquired" so that some other (better behaving) consumer can process
this message.
1) So far, it seems that RabbitMQ will only alter messages that have
been previously been "acquired" back to "not acquired" ONLY when the
original consumer's *channel* has been terminated (for some reason;
i.e., network error). I have not been able to get RabbitMQ to perform
this same type of "recovery" for any consumers that mimic the behavior
of poorly written applications (i.e., the channel stays alive, but a
fault in the underlying application logic of one consumer prevents
proper message delivery to properly functioning consumers).
2) Is there any reference in the AMQP specification for dealing with
these situations? If RabbitMQ does implement some sort of timeout (as
previously stated), what is the default time delay?
3) Is it possible that in order to achieve this type of behavior, you
have to use transactions (tx) or distributed transactions (dtx) in
RabbitMQ?
Thanks for your help,
-- Darien
More information about the rabbitmq-discuss
mailing list