Cing
发布于 2023-09-14 / 36 阅读
0

Kafka 为什么快

是什么

官网介绍 Kafka 是一个开源分布式事件流平台

一般作为中间件使用,通过 Kafka 来发布事件,订阅事件,达到削峰填谷,解耦的效果

主要概念和术语

Producers: 生产者,用于发布事件

Consumer: 消费者,用于消费事件

Topic: 可以理解为文件夹的概念,生产者和消费者都需要指定 Topic 来进行生产/消费活动

Broker: 可以理解为部署了 Kafka 的一台机器,高可用正是依赖于分布式

Partition: 分区,同一个 Topic 的数据是分布在不同的分区上的,可以通过指定 key 的方式来确保相同 key 的数据分布在同一个 Partition

设计

持久化

Kafka 的数据是持久化在硬盘上的,在普遍认知中,硬盘的速度是非常慢的,尤其是机械硬盘,那 Kafka 又是如果做到高吞吐的呢

6 个 7200 转 SATA RAID-5 阵列在顺序写的情况下可以达到 600MB/s 但是随机写只能 100k/s,这其中差了 6000 倍的性能

因此 Kafka 通过顺序写的方式在硬盘上也能做到非常高的吞吐量

常量复杂度

由于消息队列的特性,取数据从队列头取,加入数据加入到队列尾,这种操作的时间复杂度都是 O(1) 因此性能很高

不像数据库,需要维护 B-Tree 结构来提升查找速度

效率

批处理

频繁的小 I/O 操作和字节拷贝是影响性能的重要因素

Kafka 通过批处理的方式来解决频繁小 I/O 造成的性能问题

零拷贝

可参考:Efficient data transfer through zero copy - IBM Developer

Kafka 通过使用操作系统提供的零拷贝接口来减少字节拷贝次数

一次从文件读数据写到 socket 的流程

Pasted image 20230715155842.png

  1. 操作系统从硬盘中读取数据到内核空间的 pagecache
  2. 应用从内核空间读数据到用户空间的 buffer
  3. 应用将用户空间 buffer 中的数据写入内核空间的 socket buffer
  4. 操作系统将数据从 socket buffer 拷贝到 NIC buffer 中用于通过网络发送

上下文切换示意图

Pasted image 20230715160433.png

能看到,总共有 4 次数据拷贝,4 次上下文切换

使用零拷贝之后流程变更如下

Pasted image 20230715160322.png

上线文切换变更如下

Pasted image 20230715160541.png

拷贝次数从 4 减少到 3 ,上下文切换次数从 4 减少到 2

如果您的网卡支持 gather ,可以进一步优化流程

Pasted image 20230715160729.png

总共 2 次 DMA 拷贝,2 次上下文切换

端到端批量压缩

在消息队列场景下,CPU 和硬盘通常不是瓶颈,网络带宽才是

单条数据压缩对比批量数据压缩的压缩比是较差的,因为数据重复度越高,压缩才越有意义

例如 json 数据的 key 大都是相同的,多条一起压缩明显能获得更高的压缩比

Kafka 可以自动进行批量压缩

消息传输语义

  • At most once - 消息可能会丢失,但绝不会重复
  • At least once - 消息一定不会丢失,但可能会重复
  • Exactly once - 每个消息仅被投递一次

Kafka 默认提供 At least once 的消息投递保证

Kafka 0.11.0 版本之后可以使用事务来保证 Exactly once 效果(需要使用的 Connector 支持)

Kafka 为什么快

  1. 本身的特性:队列的头尾操作时间复杂度均为 O(1)
  2. 硬盘顺序写:顺序写比随机写快数千倍
  3. 零拷贝:普通拷贝有 2 次 CPU copy,2 次 DMA copy,4 次上下文切换。使用零拷贝技术后减少为 2 次 DMA copy,2 次上下文切换
  4. 批处理:将多次小 I/O 打包处理
  5. 批量压缩:自动批量压缩数据,减少传输消耗
  6. 分布式:多台 Broker 分布式处理