当前位置: 首页 > 知识库问答 >
问题:

带有AMQP和RabbitMQ的Spring,带有可选x-死信交换的队列

皇甫通
2023-03-14

我在RabbitMQ中创建了一个现有队列。它可以使用或不使用参数创建。我正在使用RabbitTemplate在Spring创建此队列的消费者。声明队列时,我不想指定x-dead-letter-exchange参数。我想让模板自己搞清楚,或者不在乎。我从消费者那里抛出AmqpRejectAndDontRequeueException来指示错误消息,但我希望队列的创建者负责决定是否为被拒绝的消息创建交换和队列。

下面是我在Spring中声明队列的bean:

@Bean
Queue queue() {
    Map<String, Object> args = new HashMap<>();
    // set the queue with a dead letter feature
    args.put("x-dead-letter-exchange", REJECTED_EXCHANGE);
    args.put("x-dead-letter-routing-key", REJECTED_ROUTING_KEY);
    Queue queue = new Queue(Constants.QUEUE_NAME, false, false, false, args);
    return queue;
}

这很好,但当队列的创建者决定不使用死信功能时,我看到以下错误:

Channel shutdown: channel error; protocol method: #method<channel.close>
(reply-code=406, reply-text=PRECONDITION_FAILED - 
inequivalent arg 'x-dead-letter-exchange' for queue 'queueName'

消息有点长,它继续告诉我哪一方有哪一个x-dead-letter-exchange(无或交易所名称)。我尝试了不同的组合(例如,使用exchange创建队列,但不在Spring中指定它,或者在不使用exchange的情况下创建队列,并在Spring中指定它),只是为了看到此消息的不同变体。

如何声明队列,使其只接受队列中已设置的任何参数?

共有3个答案

曹旭
2023-03-14

是的。当您在RabbitMQ中手动创建交换或队列,然后您的应用程序尝试创建其他交换时,就会发生此类问题。它会发现相同的队列或具有不同属性/配置的交换,因此显示配置不匹配。

解决方案:

仅允许应用程序创建Exchange和队列。

希望这有帮助。

陈嘉荣
2023-03-14

正如您在spring文档中所看到的:RabbitMQ代理将不允许声明具有不匹配参数的队列 ,因此无法执行
在RabbitMQ Java API中,有一种方法可以检查队列是否已经存在:queueDeclarePassive。

如果Spring AMQP API提供了类似的功能,那么您可以在尝试声明队列之前使用它。

仲浩旷
2023-03-14

是的,可能的原因是-如果您手动声明一些队列,然后您的程序(代码中的客户端)尝试创建一个队列(基于代码中的设置),则会出现此错误。背后的原因是当您的代码(客户端应用程序)尝试访问一个队列时。它从服务器获取一个信号,表明此连接不可用。

来解决这个问题

  • 删除您手动创建的所有队列,并让客户端程序自己创建它们
  • 如果您在删除队列时遇到问题,因为队列中存在一些数据,或者出于某种原因,您希望维护它,手动创建一个队列,并通过队列的“移动”选项卡移动其中要删除的所有队列数据
 类似资料:
  • 就像“休斯顿我们这里有一个问题”,在第一次尝试处理事件失败后,我需要安排/延迟消息5分钟。我已经在这个场景中实现了死信交换。 失败的消息会路由到DLX-->Retry队列,并在TTL 5分钟后返回工作队列进行另一次尝试。 下面是我正在使用的配置: producer.java: consumer.java:

  • 我正在使用带有Avro和汇流模式注册表的Spring云流。我正在为所有服务使用一个单独的DLQ主题,因此具有不同模式的消息可能会落在这个主题中。我已禁用动态架构注册,以确保不传递错误消息()。 然而,问题是由于dlq上缺少模式,我可能会在进入这个主题时丢失一条消息。因此,我希望能够以JSON格式向dlq生成消息,并在管道的其余部分使用Avro。如果有人能帮助我如何做到这一点,或者能为我指出这件事的

  • 我想在负载均衡器后面设置一个rabbitmq集群,并使用spring AMQP连接到它。问题: > spring客户端是否需要知道RMQ集群中每个节点的地址,或者只知道负载均衡器的地址就足够了。 如果Spring客户端只知道负载均衡器,那么它将如何为集群中的每个节点维护连接/连接工厂。 是否有任何代码示例,说明如何使spring客户端与负载均衡器一起工作。

  • 我有一个Spring RESTendpoint,具有如下所示的可选请求参数: 当我试图测试这个使用Mockito框架的endpoint时 提前感谢!

  • 我在我的消费者体内抛出一个AMQP异常。我的期望是,消息将以FIFO顺序返回队列,并在将来的某个时候重新处理。 Spring AMQP似乎没有将消息释放回队列。而是一次又一次地尝试重新处理失败的消息。这会阻止处理新到达的消息。卡在AMQP控制台内的设备将永远处于“未打包”状态。 有什么想法吗?

  • 今天,我使用Spring Cloud Streams和RabbitMQ,根据本文档编写了以下代码: 我的接口: 和我的属性文件: