基于磁盘的Kafka为什么这么快
专注于Java领域优质技术,欢迎关注
作者: Wyman 大数据手稿笔记
Kafka是大数据领域无处不在的消息中间件,目前广泛使用在企业内部的实时数据管道,并帮助企业构建自己的流计算应用程序。Kafka虽然是基于磁盘做的数据存储,但却具有高性能、高吞吐、低延时的特点,其吞吐量动辄几万、几十上百万,这其中的原由值得我们一探究竟。本文属于Kafka知识扫盲系列,让我们一起掌握Kafka各种精巧的设计。
顺序读写
众所周知Kafka是将消息记录持久化到本地磁盘中的,一般人会认为磁盘读写性能差,可能会对Kafka性能如何保证提出质疑。实际上不管是内存还是磁盘,快或慢关键在于寻址的方式,磁盘分为顺序读写与随机读写,内存也一样分为顺序读写与随机读写。基于磁盘的随机读写确实很慢,但磁盘的顺序读写性能却很高,一般而言要高出磁盘随机读写三个数量级,一些情况下磁盘顺序读写性能甚至要高于内存随机读写,这里给出著名学术期刊 ACM Queue 上的一张性能对比图:
磁盘的顺序读写是磁盘使用模式中最有规律的,并且操作系统也对这种模式做了大量优化,Kafka就是使用了磁盘顺序读写来提升的性能。Kafka的message是不断追加到本地磁盘文件末尾的,而不是随机的写入,这使得Kafka写入吞吐量得到了显著提升。
Page Cache
为了优化读写性能,Kafka利用了操作系统本身的Page Cache,就是利用操作系统自身的内存而不是JVM空间内存。这样做的好处有:
- 避免Object消耗:如果是使用Java堆,Java对象的内存消耗比较大,通常是所存储数据的两倍甚至更多。
- 避免GC问题:随着JVM中数据不断增多,垃圾回收将会变得复杂与缓慢,使用系统缓存就不会存在GC问题。
相比于使用JVM或in-memory cache等数据结构,利用操作系统的Page Cache更加简单可靠。首先,操作系统层面的缓存利用率会更高,因为存储的都是紧凑的字节结构而不是独立的对象。其次,操作系统本身也对于Page Cache做了大量优化,提供了write-behind、read-ahead以及flush等多种机制。再者,即使服务进程重启,系统缓存依然不会消失,避免了in-process cache重建缓存的过程。
通过操作系统的Page Cache,Kafka的读写操作基本上是基于内存的,读写速度得到了极大的提升。
零拷贝
这里主要讲的是Kafka利用linux操作系统的 "零拷贝(zero-copy)" 机制在消费端做的优化。首先来了解下数据从文件发送到socket网络连接中的常规传输路径:
- 操作系统从磁盘读取数据到内核空间(kernel space)的Page Cache
- 应用程序读取Page Cache的数据到用户空间(user space)的缓冲区
- 应用程序将用户空间缓冲区的数据写回内核空间到socket缓冲区(socket buffer)
- 操作系统将数据从socket缓冲区复制到网络发送的NIC缓冲区
这个过程包含4次copy操作和2次系统上下文切换,性能其实非常低效。linux操作系统 "零拷贝" 机制使用了sendfile方法,允许操作系统将数据从Page Cache 直接发送到网络,只需要最后一步的copy操作将数据复制到 NIC 缓冲区,这样避免重新复制数据。示意图如下:
通过这种 "零拷贝" 的机制,Page Cache 结合 sendfile 方法,Kafka消费端的性能也大幅提升。这也是为什么有时候消费端在不断消费数据时,我们并没有看到磁盘io比较高,此刻正是操作系统缓存在提供数据。
分区分段
Kafka的message是按topic分类存储的,topic中的数据又是按照一个一个的partition即分区存储到不同broker节点。每个partition对应了操作系统上的一个文件夹,partition实际上又是按照segment分段存储的。这也非常符合分布式系统分区分桶的设计思想。
通过这种分区分段的设计,Kafka的message消息实际上是分布式存储在一个一个小的segment中的,每次文件操作也是直接操作的segment。为了进一步的查询优化,Kafka又默认为分段后的数据文件建立了索引文件,就是文件系统上的.index文件。这种分区分段+索引的设计,不仅提升了数据读取的效率,同时也提高了数据操作的并行度。
总 结
总结起来,Kafka采用顺序读写、Page Cache、零拷贝以及分区分段等这些设计,再加上在索引方面做的优化,另外Kafka数据读写也是批量的而不是单条的,使得Kafka具有了高性能、高吞吐、低延时的特点。这样,Kafka提供大容量的磁盘存储也变成了一种优点。由于本人才粗学浅,表述有误的地方欢迎指教。
来源:真相只有一个
基于磁盘的Kafka为什么这么快的更多相关文章
- 为什么Kafka速度那么快
Kafka的消息是保存或缓存在磁盘上的,一般认为在磁盘上读写数据是会降低性能的,因为寻址会比较消耗时间,但是实际上,Kafka的特性之一就是高吞吐率. 即使是普通的服务器,Kafka也可以轻松支持每秒 ...
- 为什么 Kafka 速度那么快?
来源:cnblogs.com/binyue/p/10308754.html Kafka的消息是保存或缓存在磁盘上的,一般认为在磁盘上读写数据是会降低性能的,因为寻址会比较消耗时间,但是实际上,Kafk ...
- 白瑜庆:知乎基于Kubernetes的kafka平台的设计和实现
欢迎大家前往腾讯云+社区,获取更多腾讯海量技术实践干货哦~ 本文首发在云+社区,未经许可,不得转载. 自我介绍 我是知乎的技术中台工程师,现在是负责知乎的存储相关组件.我的分享主要基于三个,一个是简单 ...
- oracle 11g 基于磁盘的备份rman duplicate
基于磁盘的备份rman duplicate 命令创建standby database 前提条件: 确保原始库数据库的备份.存档standby 结束是完全可见, 这里,如果原始文库和靶 - 侧数据文件, ...
- HyperLedger Fabric基于zookeeper和kafka集群配置解析
简述 在搭建HyperLedger Fabric环境的过程中,我们会用到一个configtx.yaml文件(可参考Hyperledger Fabric 1.0 从零开始(八)--Fabric多节点集群 ...
- 给ambari集群里的kafka安装基于web的kafka管理工具Kafka-manager(图文详解)
不多说,直接上干货! 参考博客 基于Web的Kafka管理器工具之Kafka-manager的编译部署详细安装 (支持kafka0.8.0.9和0.10以后版本)(图文详解)(默认端口或任意自定义端口 ...
- 基于Web的Kafka管理器工具之Kafka-manager启动时出现Exception in thread "main" java.lang.UnsupportedClassVersionError错误解决办法(图文详解)
不多说,直接上干货! 前期博客 基于Web的Kafka管理器工具之Kafka-manager的编译部署详细安装 (支持kafka0.8.0.9和0.10以后版本)(图文详解) 问题详情 我在Kaf ...
- 基于Web的Kafka管理器工具之Kafka-manager安装之后第一次进入web UI的初步配置(图文详解)
前期博客 基于Web的Kafka管理器工具之Kafka-manager的编译部署详细安装 (支持kafka0.8.0.9和0.10以后版本)(图文详解) 基于Web的Kafka管理器工具之Kafka- ...
- 基于Web的Kafka管理器工具之Kafka-manager的编译部署详细安装 (支持kafka0.8、0.9和0.10以后版本)(图文详解)(默认端口或任意自定义端口)
不多说,直接上干货! 至于为什么,要写这篇博客以及安装Kafka-manager? 问题详情 无奈于,在kafka里没有一个较好自带的web ui.启动后无法观看,并且不友好.所以,需安装一个第三方的 ...
随机推荐
- JDK8~JDK11的新特性
#JDK 1.8 新特性接口中的静态方法 只能由接口自己调用 接口中的默认方法 可以不被覆盖 #JDK 1.9 新特性(可能在JDK8中被忽略了,没来得及加)接口可以定义私有方法,但是只能让自己调用, ...
- 基于AQS自己实现一个同步器
前面说了这个多,我们可以自己尝试实现一个同步器,我们可以简单的参考一下ReentrantLock这个类的实现方式,我们就简单的实现一个不可重入的独占锁吧! 一.简单分析ReentrantLock的结构 ...
- DataTable.Copy()
DataTable dtpocopy = dtPO.Copy(); DataRow[] dr = dtpocopy .Select("客户名称='" + cusName + &qu ...
- Educational Codeforces Round 63 选做
D. Beautiful Array 题意 给你一个长度为 \(n\) 的序列.你可以选择至多一个子段,将该子段所有数乘上给定常数 \(x\) .求操作后最大的最大子段和. 题解 考虑最大子段和的子段 ...
- 反射①:如何获取class对象六种方法
获取class对象的六种方法 了解:class类——是Java反射机制的入口,封装了一个类或接口的运行信息,通过调用Class类的方法可以获取这些信息,其特点如下: 1.该类在java.lang包中: ...
- 九九乘法表的四种三角形排布方式(for循环以及while循环的互换)
#region //右上 for (int i = 1; i <= 9; i++){ for (int j = 1; j <= 9; j++){ if (i > j){ Consol ...
- tornado peewee_async
https://peewee-async.readthedocs.io/en/latest/peewee_async/examples.html https://www.cnblogs.com/Vic ...
- UVA - 10382 Watering Grass(几何)
题意:有一个矩形,n个圆.已知矩形的长宽和圆的半径,问最少需多少个圆将矩形完全覆盖. 分析: 1.首先求圆与矩形的长的交点,若无交点,则一定不能对用最少的圆覆盖矩形有贡献. 2.如果两个圆与矩形相交所 ...
- Shell脚本之awk篇
目录:一.概述二.awk基本语法格式三.awk基本操作四.awk条件及循环语句五.awk函数六.awk演示示例(源自于man手册) 一.概述 1. 产品概述: awk是一种编程语言,用于在linux/ ...
- 4. 异步多级缓存架构+nginx数据本地化渲染