使用Spring Boot应用程序的RabbitMQ集群节点故障

问题描述

我有一个Spring Boot应用程序,该应用程序连接到RabbitMQ集群(作为Cloud Foundry中的一项服务)。当群集中的主节点发生故障时,由于某种原因该节点无法启动,但是应用程序(消息使用者)尝试连接至故障节点,并且不尝试连接至其他可用节点。有人可以建议一些弹簧配置来解决此问题吗?

17:36:23.829: [APP/PROC/WEB.0] Caused by: com.rabbitmq.client.ShutdownSignalException: channel error; protocol method: #method<channel.close>(reply-code=404,reply-text=NOT_FOUND - home node 'rabbit@rad33f2b1-mq-1.node.dc1.svvc' of durable queue 'Failed_ORDER' in vhost '/' is down or inaccessible,class-id=50,method-id=10)

'rabbit@rad33f2b1-mq-1.node.dc1.svvc'是失败的节点。

为了在失败时继续尝试连接到节点,我具有以下spring配置。 spring.rabbitmq.listener.simple.missing-queues-fatal = false

@Configuration
public class MessageConfiguration {

public static final String Failed_ORDER_QUEUE_NAME = "Failed_ORDER";

public static final String EXCHANGE = "directExchange";

@Bean
public Queue FailedOrderQueue(){
    return new Queue(Failed_ORDER_QUEUE_NAME);
}

@Bean
public DirectExchange directExchange(){
    return new DirectExchange(EXCHANGE,true,false);
}

@Bean
public Binding secondBinding(Queue FailedOrderQueue,DirectExchange directExchange){
    return BindingBuilder.bind(FailedOrderQueue).to(directExchange).with(Failed_ORDER_QUEUE_NAME);
}

}

解决方法

当您使用具有错误主定位符的非HA自动删除队列时,会发生这种情况。

如果主定位器不是client-local,则可能在与我们连接的节点不同的节点上创建自动删除队列。在这种情况下,如果主机节点出现故障,则会出现此问题。

为避免自动删除队列出现此问题,请将x-queue-master-locator队列参数设置为client-local或在代理上设置策略以对与此名称匹配的队列执行相同操作。

但是,您没有使用自动删除队列...

@Bean
public Queue failedOrderQueue(){
    return new Queue(FAILED_ORDER_QUEUE_NAME);
}

在使用群集和非HA队列时,该队列不会被复制,因此,如果拥有节点发生故障,您将收到此错误,直到拥有节点恢复正常。

为避免此问题,请设置策略以使队列成为镜像(HA)队列。

https://www.rabbitmq.com/ha.html