![cover](http://image.wzoe.fun/i/2024/06/09/6665758638cd8.png)
Kafka
消息队列的作用
异步、削峰填谷、解耦
基本概念
producer
生产者在默认情况下把消息均衡地分布到主题的所有分区上:直接指定消息的分区
根据消息的key散列取模得出分区
轮询指定分区。
consumer
消费者通过偏移量来区分已经读过的消息,从而消费消息。把每个分区最后读取的消息偏移量保存在Zookeeper 或Kafka上,如果消费者关闭或重启,它的读取状态不会丢失。broker
连接生产者和消费者,单个broker可以轻松处理数千个分区以及每秒百万级的消息量。broker接收来自生产者的消息,为消息设置偏移量,并提交消息到磁盘保存。
broker为消费者提供服务,响应读取分区的请求,返回已经提交到磁盘上的消息。
topic
通过主题进行分类,类似数据库中的表。consumer group
消费组保证每个分区只能被一个消费者使用,避免重复消费。如果群组内一个消费者失效,消费组里的其他消费者可以接管失效消费者的工作再平衡,重新分区。partition
Topic可以被分成若干分区分布于kafka集群中,方便扩容
单个分区内是有序的,partition设置为一才能保证全局有序
offset
生产者offset,消息写入的时候,每一个分区都有一个offset,即每个分区的最新最大的offset。
消费者offset,不同消费组中的消费者可以针对一个分区存储不同的Offset,互不影响。
副本Replicas
每个主题被分为若干个分区,每个分区有多个副本。
集群
每隔分区都有一个首领,当分区被分配给多个broker时,会通过首领进行分区复制。
LogSegment
一个分区由多个LogSegment组成,
一个LogSegment由.log .index .timeindex组成
.log追加是顺序写入的,文件名是以文件中第一条message的offset来命名的
.Index进行日志删除的时候和数据查找的时候可以快速定位。
.timeStamp则根据时间戳查找对应的偏移量。
kafka特点
高吞吐量、低延迟:kafka每秒可以处理几十万条消息,它的延迟最低只有几毫秒,每个topic可以分多个partition,由多个consumer group对partition进行conse操作
可扩展性:kafka集群支持热扩展
持久性、可靠性:消息被持久化到本地磁盘,并且支持数据备份防止数据丢失
容错性:允许集群中节点失败(若副本数量为n,则允许n-1个节点失败)
高并发:支持数千个客户端同时读写
kafka为什么快
分布式架构:可以将数据分布到多个节点上进行处理,从而实现数据的水平扩展和负载均衡,能够处理大量的消息数据
零拷贝:在数据传输过程中,避免将数据从内核空间复制到用户空间,直接将数据从发送方的内存映射到接受方的内存,避免了数据的多次复制和传输,提高了数据传输的效率。
批量发送:支持批量发送,即将多个消息一起发送到服务器端,减少了网络传输的开销,同时也减少了磁盘I/O次数,提高了数据传输的效率。
数据压缩:可以将消息在发送前进行压缩,减小消息体积,提高网络传输的效率。
消息存储:采用持久化的消息存储方式,将消息保存到磁盘中,保证了数据的可靠性和恢复性,同时也避免了内存容量的限制。
总结:kafka速度的秘诀在于,他把所有的消息都变成一个批量的文件,并且进行合理的批量压缩,减少网络IO损耗,通过mmap提高IO速度,写入数据的时候由于单个Partion是末尾添加所以速度最优;读取数据的时候配合sendfile直接暴力输出。
kafka设计
磁盘性能
持久化,kafka对消息的存储和缓存严重依赖文件系统,顺序磁盘访问在某些情况下比随机内存访问还要快,kafka的持久化队列建立在简单的读取和向文件后追加的两种操作,这种架构优点在于所有操作复杂度都是O(1),而且读写操作不会阻塞。
kafka建立在JVM之上,JVM对象内存开销很高,随着堆中数据增加,java垃圾回收会变慢,相比于维护尽可能多的 in-memory cache,并且在空间不足的时候匆忙将数据 flush 到文件系统,我们把这个过程倒过来。所有数据一开始就被写入到文件系统的持久化日志中,而不用在 cache 空间不足的时候 flush 到磁盘。实际上,这表明数据被转移到了内核的 pagecache 中。
支持批量发送,可以配置批量的大小和延迟时间(比如64K,10ms)
通过少许的延迟来极大的提升性能,这个简单的优化对速度有着数量级的提升。
批处理允许更大的网络数据包,更大的顺序读写磁盘操作,连续的内存块等等。
减少了网络多次传输的开销
减少了磁盘I/O次数,大量的小型操作I/O
零拷贝
使用linux的sendFile系统调用减少了数据拷贝和上下文切换
传统的读写操作需要四次copy操作,两次系统调用,4次上下文切换,kafka只需要一次copy,从pagecache到NIC缓冲区。
数据压缩
某些情况下,数据传输的瓶颈不是CPU,也不是磁盘,而是网络带宽。kafka以高效的批处理格式支持一批消息可以压缩到一起发送到服务器。这批消息将以压缩格式写入,并且在日志中保持压缩,只会在consumer消费时解压缩。
分布式架构,支持集群部署,多个分区。
kafka是如何保证可靠性和一致性
写入确认机制ACK,0,1,all
复制机制,每个分区的副本被复制到多个broker上,当主副本故障时,kafka自动将副本升到主副本,不会导致数据丢失
ISR 机制,Kafka维护一个ISR列表,其中包含了所有和主副本保持同步的副本,只有ISR列表中的副本才能被选举为主副本。
消费者确认机制,ack