Rebalance机制
何为Rebalance,Rebalance即再均衡,是指,将一个Topic下的多个Queue在同一个ConsumerCroup(消费者集群)中的多个Consumer间进行从新分配的过程,实际上如下
消费者集群中有两个消费者时,consumer1订阅Queue0、1、2,consumer2订阅Queue3、4
当我们消费者集群中新加了一个消费者,那么订阅关系如下,即consumer1订阅Queue0、1,consumer2订阅Queue2、3,consumer3订阅Queue3
当我们有增加一个消费者,那么订阅关系又会变成下面这样,即consumer1订阅Queue0、1,consumer2订阅Queue2,consumer3订阅Queue3,consumer4订阅Queue4
此时我们在增加一个消费者,那么订阅关系又会变化如下!即每个消费者订阅一个Queue
那么这种订阅关系变化的过程就称为Rebalance,这里补充一点,一个队列最多只能被一个消费者订阅,一个消费者则可以订阅多个队列,也就是如果我们在添加一个消费者consumer6,那么这个时候consumer6是没有Queue可以订阅的,那么consumer6也就没有消息可以接收!
Rebalance机制的本意是为了提升消息的并行消费能力,就如上面几张图片中消费者与Queue订阅关系的改变,从而提升消息的并行消费能力。
Rebalance限制
由于一个队列最多分配给一个消费者,因此当某个消费者组下的消费者实例数量大于队列的数量时,多余的消费者将分配不到任何队列,荣誉造成消费者空耗!
Rebalance危害
Rebalance在提升消费能力的同时,带来如下问题
- 消费暂停:在只有一个consumer时,其负责消费所有队列,在新增了一个consumer后会出发Rebalance的发生,此时原consumer就需要暂停部分队列的消费,等到这些队列分配给新的consumer后,这些暂停消费的队列才能继续消费
- 消费重复:consumer在消费新分配给自己队列时,必须接着之前consumer提交的消费进度的offset继续消费,然而默认情况下,offset是异步提交,这个异步性导致提交到Broker的offset与consumer实际消费的消息并不一致,这个不一致的差值就可能会重复消息消费(这里消费者并不是每次只获取一条消息,而是批量获取的)
同步提交:consumer提交了其消费完毕的一批消息的offset给broker后,需要等待broker的成功ACK,当收consumer到ACK后consumer才会继续获取并消费下一批消息,在等待ACK期间,consumer是阻塞的
异步提交:consumer提交了其消费完毕的一批消息的offset给broker后,不需要等待broker的成功ACK,consumer可以直接获取并消费下一批消息。
读取数量:对于一次读取消息的数量,需要根据具体业务选择一个相对均衡的是很有必要的,因为数量过大,系统性能提升了,但产生重复消费数量可能会增加,数量过小,系统性能会下降,但被重复消费的消息数量可能会减少!
- 消费突刺:由于Rebalance可能导致重复消费,如果需要重复消费的消息过多,或者因为Rebalance暂停时间过长从而导致积压部分消息,那么有可能导致在Rebalance结束之后瞬间需要消费个不多消息
Rebalance产生原因
导致Rebalance产生的原因,无非两个,一个是消费则订阅Topic的Queue数量发生变化,另一个是消费者组中的消费者数量发生变化。
Queue数量发生变化的场景
Broker扩容、缩容
Broker升级运维
Broker与NameServer间的网络异常波动
Queue扩容、缩容
Consumer数量发生变化的场景
Consumer扩容、缩容
Consumer升级运维
Consumer与NameServer间的网络异常波动
Rebalance过程
在Broker中维护着多个Map集合,这些集合中动态存储着当前Topic中Queue的信息,Consumer Group中Consumer实例的信息,一旦发现消费者所订阅的Queue数量发生变化,或者消费者组中的消费者数量发生变化,立即想Consumer Group中的每个实例发出Rebalance通知,Consumer实例在接收到通知后会采用Queue分配算法自己获取到对应的Queue,即由Consumer实例自主进行Consumer