搞透 Kafka 的存储架构,看这篇就够了

本文详细探讨了Kafka的存储架构设计,包括选择基于日志存储的原因、存储选型的思考、日志存储结构、日志系统架构设计、日志格式演变以及日志清理和压缩机制。Kafka主要通过顺序追加写日志和稀疏索引来实现高并发、高效存储和检索。文章还介绍了磁盘IO性能、PageCache和零拷贝技术在Kafka中的应用,揭示了Kafka处理海量数据流背后的设计原理。
摘要由CSDN通过智能技术生成

今天聊聊 Kafka 的存储系统架构设计。说到存储系统,大家可能对 MySQL 比较熟悉,也知道 MySQL 是基于 B+ 树来作为它的索引数据结构。

Kafka 又是基于什么机制来存储?为什么要设计成这样?它解决了什么问题?又是如何解决的?里面又用到了哪些高大上的技术?

带着这些疑问,我们就来和你聊一聊 Kafka 存储架构设计背后的深度思考和实现原理。

认真读完这篇文章,相信你会对 Kafka 存储架构有更加深刻的理解,也能有思路来触类旁通其他存储系统的架构。

1 Kafka 存储场景剖析

在讲解 Kafka 的存储方案之前,我们先来看看 Kafka 官网给的定义:

Apache Kafka is an open-source distributed event streaming platform used by thousands of companies for high-performance data pipelines, streaming analytics, data integration, and mission-critical applications.

翻译成中文如下:

Apache kafka 是一个开源的分布式事件流处理平台,由成千上万的公司用于高性能的数据管道流分析、数据集成和关键任务的应用程序。

了解 Kafka 的老司机都知道,它是从 Linkedin 内部孵化的项目。从一开始,Kafka 就是为了解决大数据的实时日志流而生的,,每天要处理的日志量级在千亿规模。对于日志流的特点主要包括数据实时产生与海量数据存储与处理。所以,它必然要面临分布式系统遇到的高并发、高可用、高性能等三高挑战。

    

通过上面的背景可以得出:一切脱离业务场景谈架构设计都是耍流氓

     

综上我们看对于 Kafka 的存储需求来说,要保证以下几点:

  • 存储的主要是消息流,可以是简单的文本格式也可以是其他格式。对于 Broker 存储来说,它并不关心数据本身;

  • 要支持海量数据的高效存储、高持久化,保证重启后数据不丢失;

  • 要支持海量数据的高效检索,消费的时候可以通过 offset 或者时间戳高效查询并处理;

  • 要保证数据的安全性和稳定性、故障转移容错性。

2 Kafka 存储选型

有了上面的场景需求分析后, 我们接下来分析看看 Kafka 到底基于什么机制来存储的?能否直接用现有我们了解到的关系型数据库来实现呢?我们接着继续深度分析。

     

2.1 存储基本知识

我们先来了解下存储的基本知识或者常识。在我们的认知中,对于各个存储介质的速度大体同下图中看到的那样,层级越高代表速度越快。很显然,磁盘处于一个比较尴尬的位置。然而,事实上磁盘可以比我们预想的要快,也可能比我们预想的要慢,这完全取决于我们如何使用它。

各存储介质对比分布(图来自网络)

关于磁盘和内存的 IO 速度,我们可以从下图性能测试的结果看出普通机械磁盘的顺序 I/O 性能指标是 53.2M value/s,而内存的随机 I/O 性能指标是 36.7M value/s。由此似乎可以得出结论:磁盘的顺序 I/O 性能要强于内存的随机 I/O 性能。

磁盘和内存的 IO 速度对比(图片来自网络)

         

另外从整个数据读写性能方面,有不同的实现方式,要么提高读速度,要么提高写速度。

  • 提高读速度:利用索引来提高查询速度。但是有了索引,大量写操作都会维护索引,那么会降低写入效率。常见的如关系型数据库 MySQL 等;

  • 提高写速度:这种一般是采用日志存储,通过顺序追加写的方式来提高写入速度。因为没有索引,无法快速查询,最严重的只能一行行遍历读取。常见的如大数据相关领域的基本都基于此方式来实现。

2.2 Kafka 存储方案剖析

上面从存储基础知识,以及存储介质 IO 速度、读写性能方面剖析了存储类系统的实现方式,那么我们来看看 Kafka 的存储到底该采用哪种方式来实现呢?

  

对于 Kafka 来说, 它主要用来处理海量数据流。这个场景的特点主要包括:

  • 写操作:写并发要求非常高,基本得达到百万级 TPS 顺序追加写日志即可,无需考虑更新操作;

  • 读操作:相对写操作来说比较简单,只要能按照一定规则高效查询即可(offset 或者时间戳)。

根据上面两点分析,对于写操作来说直接采用顺序追加写日志的方式就可以满足 Kafka 对于百万 TPS 写入效率要求。

但是如何解决高效查询这些日志呢? 

直接采用 MySQL 的 B+ 树数据结构存储是否可以?

我们来逐一分析下:

如果采用 B+ 树索引结构来进行存储,那么每次写都要维护索引,还需要有额外空间来存储索引,更会出现关系型数据库中经常出现的“数据页分裂”等操作。对于 Kafka 这种高并发的系统来说,这些设计都太重了,所以并不适合用。

但是在数据库索引中,似乎有一种索引看起来非常适合此场景,即哈希索引(底层基于Hash Table 实现)。为了提高读速度, 我们只需要在内存中维护一个映射关系即可。每次根据 Offset 查询消息的时候,从哈希表中得到偏移量,再去读文件就可以快速定位到要读的数据位置。但是哈希索引通常是需要常驻内存的,

  • 4
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值