订阅更新

Kafka 分区分配策略怎么选?Range、RoundRobin 和 Sticky 有什么区别?

面试问 065 约 3 分钟读完

本文目录
  1. 面试怎么回答
  2. RangeAssignor:按 Topic 分段
  3. RoundRobinAssignor:整体轮询
  4. StickyAssignor:均衡之外,尽量少移动
  5. CooperativeStickyAssignor:减少停顿范围
  6. 实际应该怎么选?
  7. 别只看策略名,要验证实际分配

面试怎么回答

Range 按 Topic 把连续分区分段,多 Topic 场景可能让前几个消费者叠加拿到更多分区;RoundRobin 在消费者间轮询,总体更均匀,但异构订阅下未必理想;Sticky 在均衡基础上尽量保留原分配,减少 Rebalance 搬迁;CooperativeSticky 进一步采用协作式交接。选择时还要看订阅结构、客户端兼容性和分区真实负载。

先把这段讲顺;面试官追问时,再展开下面的原理和细节。

详细讲解

同一个 Consumer Group 里有 3 个消费者,订阅的总分区数也不少,但实际运行时,有的消费者拿到很多分区,有的却很空闲。

这不一定是消费能力问题,也可能是分区分配策略和订阅结构不匹配。

选择策略不能只看“分得均不均”,还要同时看:按什么范围分、Rebalance 时移动多少,以及是否支持协作式交接。


RangeAssignor:按 Topic 分段

Range 会对每个 Topic 单独处理:先排序分区和消费者,再把连续的一段分区分给消费者。

它容易理解,也能让同一消费者拿到某个 Topic 的连续分区。但当多个 Topic 的分区数都不能被消费者数整除时,多出来的分区可能反复落到前几个消费者上。

比如两个 Topic 都有 3 个分区,两个消费者共同订阅:每个 Topic 都可能按 2 + 1 分配,结果是消费者 A 拿到 4 个分区,消费者 B 只有 2 个。

RoundRobinAssignor:整体轮询

RoundRobin 会把 TopicPartition 排序后,在消费者之间轮流分配,目标是让总分区数尽量平均。

当组内消费者订阅完全一致时,它通常比按 Topic 分段更均匀。但如果不同消费者订阅的 Topic 集合不同,跳过不符合订阅条件的消费者后,结果未必仍然完全均衡。

StickyAssignor:均衡之外,尽量少移动

Sticky 的目标有两个:

  1. 让分配结果尽量均衡
  2. Rebalance 后尽量保留原有分区归属

减少不必要的分区迁移,意味着消费者可以少做一些状态重建、缓存预热和位点交接。因此在成员变化较频繁、分区初始化成本较高时,Sticky 往往更实用。

CooperativeStickyAssignor:减少停顿范围

普通 Eager Rebalance 往往先让所有消费者交出分区,再重新分配。CooperativeSticky 在 Sticky 分配思想上引入协作式 Rebalance,让分区按需要逐步撤销和转移,减少全组同时停止消费的影响。

但切换策略时要确认客户端版本和组内消费者配置兼容,避免同一个 Group 中支持的策略集合不一致。

Kafka 分区分配策略对比


实际应该怎么选?

订阅简单,按 Topic 连续分区更符合预期

可以使用 Range,但要检查多个 Topic 叠加后是否让前几个消费者长期多拿分区。

消费者订阅一致,只关心总体均衡

RoundRobin 更直观。分区本身的数据量仍可能不均,所以“分区个数相同”不代表“处理负载相同”。

希望均衡,同时降低 Rebalance 搬迁

优先考虑 Sticky。

希望进一步减小 Rebalance 停顿

在版本、协议和迁移方案允许的前提下考虑 CooperativeSticky。

Kafka 分区分配策略选择指南

别只看策略名,要验证实际分配

排查时我会同时确认:

  • 每个消费者实际拿到了哪些分区
  • 各分区的 Lag、流量和单条处理成本
  • 组内订阅是否一致
  • 最近是否频繁发生成员加入、退出或超时
  • 所有消费者声明的分配策略是否兼容

如果一个热点分区的流量远高于其他分区,再均匀的 Assignor 也无法拆开这个分区。此时要处理的是分区键或分区数量,而不是继续更换分配策略。


刷题进度保存在当前浏览器