Not all messages are routed after a network failure (with Khepri) #15726
Replies: 2 comments 9 replies
-
|
@lukasfraser we need an executable way to reproduce your topology. We won't guess what exactly your topology is like, how many queues you have, and so on. So far it sounds like a combination of 2-3 known behaviors or issues. On top of that, you seemingly believe that auto-delete queues are supposed to be cleaned up when their declaring clients disconnect. That is the behavior of exclusive queues, auto-delete queues are not tied to the lifecycle of their declaring connection. Topic Exchange BindingsTopic exchange bindings with Khepri had a few known bugs addressed by Where we (or the users) knew how to reproduce this behavior with some bindings being left behind, we did. This can be the explanation of the "some messages are rejected" behavior, although what specifically "rejected" means is not clear to me. They were not routed, not rejected in the publisher confirms/DLX sense. Mass Disconnect of Clients and The Redeclaration Race™There is a widely known scenario where a mass disconnect of clients results in exclusive queues being removed concurrently with client reconnections (that include queue declarations). There is very little that RabbitMQ can do about that besides #15276. With Khepri this scenario is actually less problematic than with Mnesia, see the very first item in the Why are the
|
Beta Was this translation helpful? Give feedback.
-
|
Thank you for the reply. Regarding topology: Regarding rejection: Regarding reproducibility: For us it would be perfectly acceptable if RabbitMQ temporarily "nacks" messages while a node is leaving or joining the cluster, giving RabbitMQ some time to figure things out. Our clients will just retry publishing the message after a few seconds. However, if the system remains in this unhappy state we are quite literally blocked. Leaving us just the option of triggering the workaround that deletes & recreates the affected exchanges. |
Beta Was this translation helpful? Give feedback.







Uh oh!
There was an error while loading. Please reload this page.
-
Describe the bug
Environment
We are using RabbitMQ version 4.2.4 (Erlang 27.3.4.8) with Khepri on a Kubernetes cluster consisting of 3 nodes, where each node runs a single rabbitmq pod.
Our own process are based on C++ and Node.js with a RabbitMQ heartbeat around 5 to 10 seconds. They are deployed to the same nodes as rabbitmq.
On average we can expect around 100-200 messages per second, with peaks on startup going up to maybe 1000-2000 per second. The overall connection count is well below 100.
Usage
We create durable topic-based exchanges for publishing messages.
Consumers create classic auto-delete & exclusive queues with bindings to these exchanges.
If I am not mistaken RabbitMQ should automatically delete these queues & bindings when the consumer disconnects. To be on the safe side we also set property x-expires to 60000 (=60 seconds).
How to reproduce
When we simulate a network disconnect on one of the three nodes (e.g., disable network interface on the host machine for 3 minutes via
ip link set eth0 down; sleep 180; ip link set eth0 up) we have noticed that in some cases some (not all!) exchanges may start to cause issues.From what we can tell broken exchanges are caused by "zombie" queues & bindings within RabbitMQ (= auto-delete queues without a consumer that should have already been destroyed by RabbitMQ). Interestingly enough you can only see the "zombie" queues via the RabbitMQ Management GUI. They do not show up when calling "rabbitmqctl list_queues" in the command line. All three nodes show the same list of queues.
The "zombies" are still there after 1-2 hours.
When a message is published to an affected exchange RabbitMQ gets confused when trying to distribute messages to the affected bindings & queues:
Please note that the same rejections also occur when publishing a message via the RabbitMQ Management GUI, so it's not just our processes / libraries being unhappy. It does not appear to make any difference to which RabbitMQ pod you are connected. Client reconnects / restarts do not fix the problem. There are no relevant messages in the RabbitMQ logs. All we can see is our processes reconnecting, doing the "normal" stuff. No obvious errors.
Workaround
A workaround is to delete the exchange and recreate it. However, in order to do that you first need to reliably detect that an exchange is broken on the producer side. We do not want to trigger this unless it is absolutely necessary.
After recreating the exchange the consumer also needs to find out that its bindings to the old exchange are gone and bind to the new exchange.
We cannot use the mandatory flag for publishing updates because there are situations where we do not have any consumers.
What we have noticed is that the exchange behavior has changed between RabbitMQ 4.0.9 and 4.2.4 (both using Khepri). The same issue also occurred in 4.0.9, but less frequently.
Questions
Is this a known issue? I could not find any existing ticket that matches what we experience (aside from old issues related to Mnesia).
Are we doing something wrong in the way we are using exchanges?
Is there something else we can check?
Reproduction steps
ip link set eth0 down; sleep 180; ip link set eth0 upExpected behavior
Temporary issues / disconnects are expected due to the specific test scenario.
However, exchanges should not continue to reject messages after the network is restored.
Additional context
No response
Beta Was this translation helpful? Give feedback.
All reactions