首页 文章

Spring 季兔子每个主题的消费者

提问于
浏览
1

可以使spring-rabbit支持单个主题的多个并发消费者吗?

这是详细信息

我的系统使用手动ack模式,通过spring-rabbit进行主题交换(Spring 4.0.6) . 模式如下:

  • 消息进入ChannelAwareMessageListener

  • 工厂方法生成适当的工作程序并传入对通道的引用

  • 如果工作人员成功处理了该消息,则该消息为Ack'd

  • 如果工作程序不成功或发生异常,则消息为Nack'd并发送到死信队列以供以后处理

由于其中一些工作人员可能需要花费大量时间来完成IO绑定处理,因此我需要能够设置更多的并发使用者 .

然而,经过一些测试后,我注意到有几个消费者正在收到相同的消息 . 果然,看一下文档(http://docs.spring.io/spring-framework/docs/4.0.6.RELEASE/javadoc-api/org/springframework/jms/listener/DefaultMessageListenerContainer.html#setConcurrentConsumers-int-),证实了我的发现:

除非特定于供应商的设置措施明确允许,否则不要增加主题的并发使用者数量 . 通过常规设置,这将导致同时消耗相同的消息,这几乎是不可取的 .

我的问题如下:

  • 究竟是什么意思"unless vendor-specific setup measures clearly allow for it"是否有补丁/版本/配置或Rabbit支持这个?

  • 我可以轻松地在客户端上编写代码,以防止消息被另一个工作者处理时被处理 . 那么,我对这条消息做了什么呢?发送nack?忽略它?如果我nack然后实际处理消息的工作人员在一段时间之后发送ack会发生什么?是否会抛出异常?

提前致谢...

1 回答

  • 1

    你提到的警告是关于JMS而不是RabbitMQ . 看看Spring RabbitMQ documentation . 文档不包含此警告 .

    一旦消息被传递到队列(无论交换类型如何),消费者/工作者一次可以使用它(假设没有问题) .

    如果您收到两次相同的消息,则存在某个问题:

    • 消息被解雇并重新排队

    • 通道/连接在客户端关闭

    • 有网络问题,Rabbit自动重新排队消息(服务器和客户端关闭通道/连接)

    对于最后两点,您应该收到一些错误消息 .

    请注意,这一点在我看来是不必要的,可以解释这个问题:

    工厂方法生成适当的工作程序并传入对通道的引用

    SimpleMessageListenerContainer 已使用 Executor . 当您使用自己的执行程序时,spring-amqp通道池(如果您使用任何通道)和执行程序之间可能存在问题,例如 . 因为spring-amqp相信它不再被使用,所以该 Channels 已关闭 .

    而不是生成自己的线程,而是在当前 ChannelAwareMessageListener#onMessage 线程的同一线程上处理消息 .

相关问题