消息负载均衡策略

云消息队列 RocketMQ 版的消息负载均衡策略针对生产者和消费者有所差异。对消费者而言,消息负载均衡策略在一定程度上影响消息堆积。

背景信息

随着SDK版本的升级,云消息队列 RocketMQ 版的负载均衡策略也有所优化,根据SDK版本,负载均衡策略可分为:

负载均衡策略(客户端Java v2.x.x.Final和C++ v3.x.x)

前提条件

  • TCP协议Java SDK:

    • SDK版本:升级至2.x.x.Final版本

    • 实例所属地域:华东1(杭州)、华北1(青岛)、华北2(北京)、华北3(张家口)、华北5(呼和浩特)、华南1(深圳)、西南1(成都)、德国(法兰克福)和印度尼西亚(雅加达)。

  • TCP协议C++ SDK:

    • SDK版本:升级至3.x.x版本

    • 实例所属地域:所有地域均支持。

优势

客户端Java v2.x.x.Final和C++ v3.x.x版本的负载均衡策略有以下优势:

  • 消息消费更加灵活,不再按照Queue维度消费,同一Queue的消息可以被多个消费者消费。

  • 当消费者个数多于Queue的个数时,也不会产生消费者空转的现象,避免资源浪费。

生产者负载均衡策略

  • 无序消息(普通消息、事务消息、定时和延时消息):Producer将消息以轮询的方式发送至Queue,如下图所示:生产者-普通消息

    图中Msg1、Msg2代表第一条消息、第二条消息,生产者会把第一条消息发送至Queue 1,然后第二条消息发送至Queue 2,第三条消息发送至Queue 3,以此类推,第四条消息又发送至Queue 1,循环往复。

  • 顺序消息:相同Sharding Key的消息被发送至同一个Queue,如下图所示:生产者-顺序消息

    图中ShardingKey为1的消息都同时被发送到Queue1中,同样Sharding Key为2的消息同时被发送至Queue 2中。

消费者负载均衡策略

  • 无序消息:云消息队列 RocketMQ 版Broker按照消息维度将Topic中的所有消息平均分配给消费者集群中的多个消费者处理。

    客户端Java v2.x.x.Final和C++ v3.x.x版本的负载均衡不再按照Queue维度消费,同一Queue的消息可以被多个消费者消费。具体示例如下图所示:消费者-普通消息

    图中每一个Queue中的多条消息都可同时被不同的消费者消费,例如Queue 2中的四条消息被分配给了Consumer 1、Consumer 2、Consumer 3及Consumer 4消费。

  • 顺序消息:消息消费根据Sharding Key负载均衡,不同Sharding Key的消息可被均衡的负载到多个Queue中消费,且为保证顺序消息的语义,相同Sharding Key的消息会被同一个消费者消费,具体示例如下图所示:顺序消息消费策略

    说明
    • 3-1:该图标背景色表示消息属于Queue 1;Msg2-1表示该消息为Queue1中的第2条消息,且消息的ShardingKey为1。

    • 3-2:该图标背景色表示消息属于Queue 2;Msg3-2表示该消息为Queue2中的第3条消息,且消息的ShardingKey为2。

    图中Msg1-1、Msg2-1和Msg3-1这三条消息的Sharding Key都是1,因此被同一个消费者Consumer 1消费,同样Sharding Key都为2的消息同时被Consumer 2消费。

    Msg4-3和Msg4-4的Sharding Key不同,分别为3和4,因此可被分配给不同的消费者消费。

负载均衡策略(客户端Java v1.x.x.Final和C++ v1.x.x/v2.x.x)

生产者负载均衡策略

与客户端Java v2.x.x.Final和C++ v3.x.x的负载均衡策略相同,具体示例,请参见负载均衡策略(客户端Java v2.x.x.Final和C++ v3.x.x)

  • 无序消息:Producer的消息以轮询的方式发送至Queue。

  • 顺序消息:相同Sharding Key的消息被发送至同一个Queue。

消费者负载均衡策略

说明

无序消息和顺序消息的负载均衡策略相同。

云消息队列 RocketMQ 版包含Broker和Name Server等节点,其中Broker节点负责将Topic的路由信息上报至Name Server节点。

假设目前云消息队列 RocketMQ 版只有一个Broker节点,消息从Producer发送至云消息队列 RocketMQ 版的Topic,默认会将这些Topic下的消息均衡负载至8个Queue(逻辑概念)。云消息队列 RocketMQ 版Broker会将这些Queue再平均分配至属于同一个Group ID的消费者集群。

云消息队列 RocketMQ 版中,一个Queue只能同时被分配至一个消费者消费。因此,每台消费者机器处理的Queue的数量有以下几种可能:

  • 若消费者机器数量大于Queue的数量,则超出Queue数量的机器会处理0个Queue上的消息,如下图所示:消费者-1

  • 若消费者机器数量等于Queue的数量,则每台机器会处理1个Queue上的消息,如下图所示:消费者-2

  • 若消费者机器数量小于Queue的数量,则每台机器会处理多个Queue上的消息,如下图所示:消费者-3

因为消费者负载均衡策略是以Queue为粒度维护,如果消费者集群中一台机器处理变慢,可能是机器硬件、系统、远程RPC调用或Java GC等原因导致分配至此机器上的Queue的消息不能及时处理,则整个Queue上的消息都会堆积。