共计 1833 个字符,预计需要花费 5 分钟才能阅读完成。
有人说:他曾在一台配置较好的机子上对 Kafka 进行性能压测,压测后果是 Kafka 单个节点的极限解决能力靠近每秒 2000 万 条音讯,吞吐量达到每秒 600MB。
那 Kafka 为什么这么快?如何做到这个高的性能?
本篇文章次要从这 3 个角度来剖析:
- 生产端
- 服务端 Broker
- 生产端
先来看下生产端发送音讯,Kafka 做了哪些优化?
(1)生产端 Producer
先来回顾下 Producer 生产者发送音讯的流程:
- 首先指定音讯发送到哪个 Topic。
- 抉择一个 Topic 的分区 partitiion,默认是轮询来负载平衡。
- 也能够指定一个分区 key,依据 key 的 hash 值来散发到指定的分区。
- 也能够自定义 partition 来实现分区策略。
- 找到这个分区的 leader partition。
- 与所在机器的 Broker 的 socket 建设通信。
- 发送 Kafka 自定义协定格局的申请(蕴含携带的音讯、 批量音讯 )。
将思路集中在音讯发送时候,可发现这两个华点:批量音讯和自定义协定格局。
- 批量发送:缩小了与服务端 Broker 解决申请的次数,从而晋升总体的解决能力。
- 调用 send() 办法时,不会立即把音讯发送进来,而是缓存起来,抉择失当机会把缓存里的音讯划分成一批数据,按批次发送给服务端 Broker。
- 自定义协定格局:序列化形式和压缩格局都能缩小数据体积,从而节俭网络资源耗费。
各种压缩算法比照:
- 吞吐量方面:LZ4 > Snappy > zstd 和 GZIP
- 压缩比方面:zstd > LZ4 > GZIP > Snappy
(2)服务端 Broker
Broker 的高性能次要从这 3 个方面体现:
- PageCache 缓存
- Kafka 的文件布局 以及 磁盘文件程序写入
- 零拷贝 sendfile:减速生产流程
上面开展讲讲。
1)PageCache 减速音讯读写
应用 PageCache 次要能带来如下益处:
- 写入文件的时候:操作系统会先把数据写入到内存中的 PageCache,而后再一批一批地写到磁盘上,从而缩小磁盘 IO 开销。
- 读取文件的时候:也是从 PageCache 中来读取数据。
如果音讯刚刚写入到服务端就会被生产,依照 LRU 的“优先革除最近起码应用的页”这种策略,读取的时候,对于这种刚刚写入的 PageCache,命中的几率会十分高。
2)Kafka 的文件布局 以及 磁盘文件程序写入
文件布局如下图所示:
次要特色是: 文件的组织形式是“topic + 分区”,每一个 topic 能够创立多个分区,每一个分区蕴含独自的文件夹。
Kafka 在分区级别实现文件程序写 :即多个文件同时写入,更能施展磁盘 IO 的性能。
- 绝对比 RocketMQ: RocketMQ 在音讯写入时谋求极致的程序写,所有的音讯不分主题一律程序写入 commitlog 文件,topic 和 分区数量的减少不会影响写入程序。
- 弊病: Kafka 在音讯写入时的 IO 性能,会随着 topic、分区数量的增长先回升,后降落。
- 所以应用 Kafka 时,要警觉 Topic 和 分区数量。
3)零拷贝 sendfile:减速生产流程
当不应用零拷贝技术读取数据时:
流程如下:
- 生产端 Consumer:向 Kafka Broker 申请拉取音讯
- Kafka Broker 从 OS Cache 读取音讯到 应用程序的内存空间:
- 若 OS Cache 中有音讯,则间接读取
- 若 OS Cache 中无音讯,则从磁盘里读取
- 再通过网卡,socket 将数据发送给 生产端 Consumer
当应用零拷贝技术读取数据:
Kafka 应用零拷贝技术能够把这个复制次数缩小一次,间接从 PageCache 中把数据复制到 Socket 缓冲区中。
- 这样不必将数据复制到用户内存空间。
- DMA 控制器间接实现数据复制,不须要 CPU 参加,速度更快。
(3)生产端 Consumer
消费者只从 Leader 分区批量拉取音讯。
为了进步生产速度,多个消费者并行生产比不可少。Kafka 容许创立生产组 (惟一标识 group.id),在同一个生产组的消费者独特生产数据。
举个栗子:
- 有两个 Kafka Broker,即有 2 个机子
- 有一个主题:TOPICA,有 3 个分区 (0, 1, 2)
如上图,举例 4 中状况:
- group.id = 1,有一个消费者:这个消费者要解决所有数据,即 3 个分区的数据。
- group.id = 2,有两个消费者:consumer 1 消费者需解决 2 个分区的数据,consumer2 消费者需解决 1 个分区的数据
- group.id = 3,有三个消费者: 消费者数量与分区数量相等 ,刚好每个消费者解决一个分区
- group.id = 4,有四个消费者: 消费者数量 > 分区数量 ,第四个消费者则会处于闲暇状态
正文完