不重启服务 动态停止、启动RabbitMQ消费者 监听器

在消费RabbitMQ消息的过程中,有时候可能会想先暂停消费一段时间,然后过段时间再启动消费者,这个需求怎么实现呢?我们可以借助RabbitListenerEndpointRegistry这个类来实现,它的全类名是org.springframework.amqp.rabbit.listener.RabbitListenerEndpointRegistry,通过这个类可以实现全部队列消息的启动、停止消费,也可以实现指定队列消息的启动、停止消费。

停止、启动全部队列消费

RabbitListenerEndpointRegistry类提供了start()方法和stop()方法,可以看到底层都是通过调用getListenerContainers()获取到所有队列的消费监听容器列表,然后遍历挨个调用对应的start()方法和stop()方法。

java 复制代码
	@Override
	public void start() {
		for (MessageListenerContainer listenerContainer : getListenerContainers()) {
			startIfNecessary(listenerContainer);
		}
	}
 
	@Override
	public void stop() {
		for (MessageListenerContainer listenerContainer : getListenerContainers()) {
			listenerContainer.stop();
		}
	}

我们只需要获取到RabbitListenerEndpointRegistry对象,然后调用其start()方法和stop()方法即可实现启动/停止所有队列消费。

java 复制代码
//如果mq堆积,就先暂停某个队列
        if (messageCount > 180) {
            Collection<MessageListenerContainer> listenerContainers = rabbitListenerEndpointRegistry.getListenerContainers();
            for (MessageListenerContainer container : listenerContainers) {
                SimpleMessageListenerContainer con = (SimpleMessageListenerContainer) container;
                //消息监听容器要消费的队列名称集合
                List<String> queueNamesList = Arrays.asList(con.getQueueNames());
                //判断容器中的队列名称是否包含需要调整的队列名参数
                if (queueNamesList.contains(QUEUE_NAME) && con.isRunning()) {
                    log.info("暂停某某队列!");
                    con.stop();
                }
            }
        } else {
            Collection<MessageListenerContainer> listenerContainers = rabbitListenerEndpointRegistry.getListenerContainers();
            for (MessageListenerContainer container : listenerContainers) {
                SimpleMessageListenerContainer con = (SimpleMessageListenerContainer) container;
                //消息监听容器要消费的队列名称集合
                List<String> queueNamesList = Arrays.asList(con.getQueueNames());
                //判断容器中的队列名称是否包含需要调整的队列名参数
                if (queueNamesList.contains(QUEUE_NAME) && !con.isRunning()) {
                    log.info("开启某某队列!");
                    con.start();
                }
            }
        }
    }
相关推荐
Rookie小强10 分钟前
ZooKeeper和Reids做分布式锁的区别?
分布式·zookeeper·云原生
斯普信专业组11 分钟前
zookeeper因jute.maxbuffer启动异常问题排查处理
分布式·zookeeper·云原生
啥都不懂的小小白1 小时前
Dubbo从入门到实战:分布式服务开发指南
分布式·dubbo
真上帝的左手2 小时前
十、软件设计&架构-分布式-分布式事务
分布式·架构
在未来等你3 小时前
RabbitMQ面试精讲 Day 17:消费者调优与并发消费
中间件·面试·消息队列·rabbitmq
LiRuiJie4 小时前
深入剖析Seata如何实现分布式事务(主要基于AT模式)
分布式·seata·分布式事务
Zfox_4 小时前
Redis应⽤-缓存与分布式锁
服务器·数据库·redis·分布式·缓存
老四敲代码16 小时前
Kafka 生产者与消费者分区策略全解析:从原理到实践
分布式·kafka
会飞的架狗师16 小时前
【Kafka系列】第二篇| Kafka 的核心概念、架构设计、底层原理
分布式·kafka
lifallen18 小时前
Hadoop MapReduce过程
大数据·数据结构·hadoop·分布式·apache