Kafka 大规模摄取与处理 | Rajamohan Jabbala

发布: (2026年1月7日 GMT+8 16:04)
5 min read
原文: Dev.to

Source: Dev.to

Kafka 大规模摄取与处理封面图 | Rajamohan Jabbala

大多数 Kafka 故障并不是因为 Kafka 无法扩展。
它们发生是因为团队从未做过数学计算。

“良好” 的样子(先看 SLO)

一个生产环境的 Kafka 流水线应该:

  • 以低延迟处理每个主题的 N 条消息/秒
  • 通过分区、消费者、Broker 实现线性扩展
  • 保证至少一次(或恰好一次)语义
  • 通过消费者组支持 fan‑out
  • 在明确的延迟、吞吐量、持久性 SLO 范围内运行

示例 SLO

  • 生产延迟 p99 ≤ X ms
  • 消费者延迟 ≤ Y 秒(稳态)
  • 在 2 倍峰值后恢复 ≤ Z 分钟
  • 可用性 ≥ 99.9 %

如果你不定义这些,Kafka 调优就会沦为迷信。

Kafka 机制(真正重要的部分)

  • 主题通过 分区 扩展。
  • 一个分区 → 每个消费者组只能有一个消费者。
  • 多个消费者组 = 独立的重新读取(fan‑out)。

规则:
一个消费者组中有用的最大消费者数 = 分区数。
添加超过分区数的消费者 不会 提高吞吐量。

逻辑架构

Producers → orders topic (P partitions, RF=3)

Kafka cluster distributes:
  • One leader per partition
  • Replicas across brokers

Downstream consumer groups:
  • Fraud consumer group
  • Analytics consumer group
  • ML feature consumer group

Each group owns its own offsets and scales independently.

容量规划(不可或缺的步骤)

输入

符号含义
T消息/秒
S平均消息大小(字节,已压缩)
R副本因子
C每个消费者的消息/秒(测得)
H预留空间(1.3–2×)
RetentionDays保留天数

核心公式

  • 分区数P = ceil((T / C) × H)
  • 入口流量Ingress = T × S × R
  • 出口流量(每个组)Egress = T × S
  • 每日存储(仅 leader)T × S × 86,400
    再乘以 R 和保留天数即为总存储。

示例(1 M 条消息/秒)

参数
T(消息/秒)1,000,000
S(字节)200
C(消息/秒/消费者)25,000
H(预留空间)1.5
RF(副本因子)3

结果

  • 分区数:60
  • 入口流量:约 572 MB/秒
  • 每个消费者组的出口流量:约 191 MB/秒
  • 3 天保留(含副本)的存储:约 155 TB

这就是为什么“直接加 broker”不是可行的策略。

不会适得其反的分区策略

  • 使用高基数键(例如 order_id,而不是 country)。
  • 积极监控倾斜。
  • 早期稍微超分区,以免后期重新分片成本高昂。

消费者组扩展

  • 将消费者扩展到分区数 (P) 的上限。
  • 为不同的流水线使用独立的消费者组。
  • 基于延迟增长 自动扩容,而不是基于原始延迟值。

可行的可靠性默认配置

acks=all
min.insync.replicas=2   # 当 RF=3 时
enable.idempotence=true
unclean.leader.election.enable=false
# Rack/AZ 感知的副本放置
  • 仅在业务语义需要时才使用恰好一次语义。

可观测性 > 调优

监控

  • 每个分区的延迟增长
  • p95/p99 生产和消费延迟
  • 未复制完整的分区
  • 磁盘、网卡、控制器健康状况

扩容

  • 消费者 → 当延迟上升时
  • 分区 → 当消费者饱和时
  • Broker → 当磁盘/网卡压力增大时

最后总结

Kafka 并不是因为它是 Kafka 才不扩展。
它之所以能扩展,是因为你把它设计成可扩展的。

  • 数学胜过希望。
  • 测量击败神话。
Back to Blog

相关文章

阅读更多 »

系统设计:日历应用

功能需求 - 创建 event,修改 event,取消 event - 按日、周或年查看 calendar - 设置 recurring meetings - 发送 notification …