Producer flow control commented on by R John O'Hara (Jul 28, 2008).

Comment:

It is useful to this of what happens at the limits. Ultimately, a very fast publisher (Quad Xeon) publishing to a slow broker (e.g. running on a Commodore 64); middleware does not have infinite performance.

Note we may not have hit queue limits here at all, we might just be too slow. There are TWO problems i) when we are full vs ii) when we can't cope with a data rate (writing to floppy is slow on my Commodore 1541).

So what do we do?
We physically do not have the capacity in the broker to deal with the publish request, we are over run (or near it). So we preserve ourself for the benefit of consumers and other publishers.

Thinking backwards in terms of severity:
1) The ultimate sanction is to drop the publishers connection with a suitable error message. It's up to the architect to buy better hardware or build a better app. Not our problem. Aidans idea of tarpitting on reconnect might be neat here.
2) We drop a channel
3) We block the TCP connection (nasty, because its quite lumpy and doesn't give the opportunity for the publisher to behave better)
4) We return STOP messages (or add some way to say STOP FOR Xms (a protocol change would be needed)
5) We conflate messages where that is possible (this is an option in both 'too fast' and 'full up' scenarios)

The "stop" messages give the client a change to adjust its rate without fancy MT code.

If a queue is full, and a client goes to publish again, when what?
1) For transacted sessions, rollback the transaction with a Queue full indication
2) For Ack'ed sessions its trickier. We can never send the Ack honestly. Dropping the channel/connection may well be the best course of action. Remember in AMQP clients aren't supposed to get too upset by us dropping the connection.

The first scenario (my trusty C64) is rate based; and probably best handled for the whole session (not just an exchange/queue). This publisher is likely just too fast on all counts.

The second is running out of space on a queue; that's a hard condition. We can either:
1) make it go away by applying some policy to the queue (purge out TTL exceeded messages, perhaps apply implementation specific conflation of messages if the user has configured some extension e.g. replace a price with a more recent one) or its a hard condition.
2) With TX we just kill the TX and all is well, and with Acks, as discussed. This is something that is easy enough to evaluate in the Exchange/Queue posting logic (but what do I know?). Note that if a message is routed to N end points, a failure to insert to any of the N should cause a fail (logically speaking).
3) Just pause the connection indefinitely (quite a nice option if there is some prospect of someone emptying the queue).

The ability to choose between 3 and the other modes would be a nice implementation specific feature for Qpid.

Bottom line is that rate control into a exchange/rk combo us unlikely to find much use in the real world.

Thoughts?
John

Reply via email to