2.2 副本同步机制
kafka每个partition都有一个leader和若干个follower, leader对外提供读写能力,follower会不断的向leader发送请求尝试拉取数据,拉取到的数据会写入到本地磁盘。关于副本的同步机制在之前一篇中已经介绍过。
https://www.jianshu.com/p/d6bae5407d7f
2.3 kafka零拷贝机制
传统的四次拷贝机制
传统的四次拷贝
1、操作系统将数据从磁盘文件读取到内核空间
2、应用从内核空间读入到用户空间
3、应用程序将数据写入到内核空间,放入到socket缓冲区
4、操作系统将数据从socket缓冲区复制到网卡接口
四次拷贝伴随这四次上下文的切换
kafka零拷贝机制
kafka则借助操作系统的sendfile,直接将数据从一个fd传输到另一个fd.
1、网卡直接访问系统主内存,解放了CPU
2、不在需要内核态到用户态的文件拷贝和上线文切换
kafka零拷贝机制
2.4 kafka的三种消费模式
1、At most once 最多一次
第一步如果先提交offset,第二步再处理消息。如果②之前consumer宕机,则消息4不会被处理,这样就造成消息的丢失。
最多消费一次
2、At least once 最少一次
第一步如果先处理消息4,第二步再提交offset。如果②之前consumer宕机,则消息4下次会继续消费,这样就造成重复消费。
最少消费一次
3、Exactly once 精确一次
1、依赖业务来实现
即关闭offset自动提交,可以将offset作为关系型数据库的唯一索引,并将①和②放到一个事务中处理。消息处理成功同时提交offset的请求发送成功,提交事务。如果重复处理消息时,在数据库中有相同offset记录则不处理。
2、依赖kafka实现
当从一个 kafka topic 中消费并输出到另一个 topic 时 (正如在一个Kafka Streams 应用中所做的那样),我们可以使用 0.11.0.0 版本中的新事务型 producer,并将 consumer 的位置存储为一个 topic 中的消息,所以我们可以在输出 topic 接收已经被处理的数据的时候,在同一个事务中向 Kafka 写入 offset。如果事务被中断,则消费者的位置将恢复到原来的值,而输出 topic 上产生的数据对其他消费者是否可见,取决于事务的“隔离级别”。 在默认的“read_uncommitted”隔离级别中,所有消息对 consumer 都是可见的,即使它们是中止的事务的一部分,但是在“read_committed”的隔离级别中,消费者只能访问已提交的事务中的消息
附录 kafka和RabbitMQ的区别
kafka结构
一个topic会分散为多个分区存储,分区可以并发消费,所以kafka有非常高的吞吐量。
RabbitMQ结构
RabbitMQ每个broker只有一个master和一个镜像,所有的读写操作都是发生在master队列中,master的单节点导致吞吐量的下降,这是架构设计上的硬伤。
所以从架构上就能看出,如果对并发要求高的系统,选型kafka会更适合。