RabbitMQ的fanout交换机问题

11

使用发布/订阅的RabbitMQ Java教程,我可以创建一个扇出交换机,并且任何连接的消费者都将接收到消息的副本。与动态/编程方式声明交换和绑定不同,我想在连接任何消费者之前创建交换和绑定。我通过RabbitMQ管理控制台完成了这个过程。然而,由于某种原因,我的消费者是以轮询的方式接收消息,而不是全部接收消息的副本。我错过了什么?以下是一些代码片段:

发布者:

channel.basicPublish("public", "", null, rowId.getBytes("UTF-8"));

消费者:

QueueingConsumer consumer = new QueueingConsumer(channel);
            channel.basicConsume("myqueue", false, consumer);

在 RabbitMQ 管理控制台中,我创建了一个类型为“fanout”的交换机“public”,并将该交换机绑定到“myqueue”。

感谢任何帮助!

2个回答

28
这段话的意思是,似乎你的所有消费者都订阅了同一个队列。当多个消费者订阅同一个队列时,RabbitMQ 的默认行为是在所有订阅的消费者之间轮流分发消息。请参见RabbitMQ 教程#2:工作队列中的“轮询调度”。
广播交换机用于确保绑定到它的每个队列都会收到消息的副本,而不是每个消费者。如果您希望每个消费者都收到消息的副本,通常您需要让每个消费者创建自己的队列,然后绑定到交换机上。我不确定您为什么要避免编程方式创建/绑定队列,但如果您预先知道订阅者的数量并为每个订阅者创建一个队列,则可以获得相同的效果。

4
这个回答对我很有帮助,谢谢!我一直以为每个连接的消费者会收到消息的副本,而不是每个连接的队列。这解决了我的问题。再次感谢! - littleK
1
我在文档中没有找到这个解释。他们告诉我使用临时队列名称,但没有告诉我为什么。我想为每个人都使用命名为“global_messages”的队列,为什么不呢?结果它并没有起作用。将交换机设置为fanout只是拼图的一半。这就是缺失的关键信息。谢谢! - CodeOrElse

0

你应该手动为每个消费者创建新的队列,或使用以下命令随机创建非持久化队列。

var queueName = channel.QueueDeclare().QueueName;

每个消费者从相关队列名称中消费并接收所有消息。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接