kafka(一)原理(1)介绍

一、介绍

1、简介

kafka是一个分布式的基于发布\订阅模式的消息队列,主要用于大数据实时处理领域

2、基础架构简介

(1)生产者:向kafka集群发送数据

(2)broker:启动的kafka集群

(3)消费者:从kafka集群消费数据

(4)zookeeper:帮助kafka实现分布式

3、kafka的设计概要
3.1、吞吐量/延时

(1)大量使用操作系统页缓存,内存操作速度快;

(2)不直接参与IO操作,而是交由操作系统来完成;

(3)采用追加写入方式,摒弃了缓慢的磁盘随机读写操作;

(4)使用以sendfile为代表的0拷贝技术加强网络间的数据传输效率;

3.2、消息持久化
3.3、负载均衡和故障转移

(1)负载均衡:通过分区领导者选举实现。kafka默认提供了智能的leader算法,可以在集群的所有机器上以均等机会分散各个patition的leader。

(2)故障转移:每台kafka服务器启动会以会话机制把自己注册到zk上。

3.4、伸缩性
4、kafka使用场景

(1)消息传输

(2)网站行为日志追踪

(3)审计数据收集

(4)日志收集

(5)event sourcing

(6)流式处理

二、kafka topic结构

大部分的消息引擎是producer-topic-consumer,而kafka是producer-topic-partition-consumer,即kafka中topic只是业务的区分,真正的消息体是prtition。

1、topic主题

可以理解成队列,但是和点对点队列不同的是,不同的消费者组都可以从topic拉去相同的消息。

由此引出推模型和拉模型的区别:

推模型 push :指定消息推送给谁,如果要给多个对象推送的话,需要推送多份。

拉模型 pull :消息发布出去,放到某个地方,感兴趣的自己来拉。只需要推一份数据。

我们通常使用topic来区分实际业务。

2、partition分区:
2.1、介绍:

为了实现扩展性,一个非常大的topic可以分布到多个broker(即服务器)上,一个topic可以分为多个partition,每个partition是一个有序的队列。partition的数量设置为broker数量的整数倍。

一个partition在kafka上就是一个目录,目录名称为:[topicName]-[partitionNo];

一个partition可以被在不同消费者组的消费者同时消费。多个partition也可以被同一个消费者消费。

2.2、分区原因

kafka中的topic通常会被多个消费者订阅,出于性能的考量,kafka并不是topic-message的两级结构,而是采用了topic-partition-message的三级结构来分散负载。从本质上来讲,topic是由若干个partition组成的。而topic的partition是不可修改的有序消息序列,每个partitiony有自己的编号,用户对partition唯一能做的就是在消息序列的尾部追加写入消息。

说明:partition没有太多的业务含义,它的引入就是单纯的提升系统的吞吐量,创建topic时可以根据集群实际配置设置具体的partition数,实现整体性能的最大化。

(1)方便在集群中扩展(相当于负载) :每个Partition 可以通过调整以适应它所在的机器,而一个topic又可以有多个Partition组成,因此整个集群就可以适应任意大小的数据了;

(2)可以提高并发:因为可以以Partition为单位读写了;

3、topic和partition的区别:

(1)Topic是Kafka中消息的逻辑分类,可以看作是一个消息的存储类别;

(2)Partition则是Kafka 中实际保存数据的单位。每个Topic可以被划分为多个Partition,而这些 Partition 会尽量平均的分配到各个 Broker 上。当一条消息发送到Kafka时,它会被分配到一个特定的Partition中,并最终写入 Partition 对应的日志文件里。

三、replica 副本

1、原因:

partition是有序消息日志,如果只存一份,一旦保存partition的kafaka挂了,其上保存的消息也就丢失了,所以需要有备份,这些备份日志在kafka中称为副本,replica的唯一目的是防止数据丢失。每个分区都有一个或者多个副本。kafka保证同一个partition的多个replica一定不会分配在同一台broker上,否则实现不了冗余备份的效果。

2、组成

副本分为两类,领导者副本leader和追随者follower副本。如果leader所在的broker宕机,kafka会从剩余的replica中选举新的leader。

(1)leader:

每个分区可能有多个副本,但是这些副本中会选出一个leader,即多个副本中的“主”,producer向kafka发送数据时,和consumer拉取数据时都是和leader做交互,leader会和follower之间会同步数据。

(2)follower:

多个副本中的的“从”,有了副本保证数据的安全性,如果有leader挂掉,从follower选取新的leader,所以follower肯定不能和leader在同一个服务器上。

3、ISR

Kafka 中的 ISR(In-Sync Replicas)机制是一种用于确保数据可靠性和一致性的重要机制。ISR 是一组副本,它包括分区的领导者(Leader)和追随者(Follower)副本,这些副本与领导者保持数据同步。

四、Kafka中的消息日志文件

1、文件目录

kafka数据的存储位置,在config/server.properties中的log.dirs中配置;如我的为:

log.dirs=D:\\javas\\kafka\\kafka_2.12-3.5.2\\logs
2、文件结构

partition是以文件的形式存储在文件系统中,比如,创建了一个名为kafkaData的topic,有4个partition,那么在Kafka的数据目录中(由配置文件中的log.dirs指定的)中就有这样4个目录: kafkaData-0, kafkaData-1,kafkaData-2,kafkaData-3,其命名规则为<topic_name>-<partition_id>,里面存储的分别就是这4个partition的数据。

每个数据目录的子目录都有xx.index ,xx.log ,xx.timeindex三个文件组成。

这些文件都是二进制的文件,无法使用文本工具直接查看。但是,Kafka提供了工具可以用来查看这些日志文件的内容。

#1、查看timeIndex文件
$ ./kafka-dump-log.sh --files /app/kafka/kafka-logs/secondTopic-0/00000000000000000000.timeindex 
#2、查看index文件
$ ./kafka-dump-log.sh --files /app/kafka/kafka-logs/secondTopic-0/00000000000000000000.index
#3、查看log文件
$ ./kafka-dump-log.sh --files /app/kafka/kafka-logs/secondTopic-0/00000000000000000000.log

 (1) .log结尾的就是实际存储消息的日志文件,大小固定为1G(由参数log.segment.bytes参数指定),写满后就会新增一个新的文件。一个文件也成为一个segment文件名表示当前日志文件记录的第一条消息的偏移量。

(2).index和.timeindex是日志文件对应的索引文件。不过.index是以偏移量为索引来记录对应的.log日志文件中的消息偏移量。而.timeindex则是以时间戳为索引。

index文件的作用类似于数据结构中的跳表,他的作用是用来加速查询log文件的效率。而timeindex文件的作用则是用来进行一些跟时间相关的消息处理。比如文件清理。

​ 这两个索引文件也是Kafka的消费者能够指定从某一个offset或者某一个时间点读取消息的原因。

(3)另外的两个文件,partition.metadata简单记录当前Partition所属的cluster和Topic。leader-epoch-checkpoint文件参见上面的epoch机制。

3、消息日志的分段(log文件记录方式)

为了防止消息日志不断追加使得文件过大,导致检索效率变低,一个Partiton又被划分多个Segment来组织数据,在磁盘上,每个Segment由一个存储消息的消息日志log文件和两个索引文件组成,每个日志文件包含一个或多个消息。每个日志文件的命名规则为"{baseOffset}.log",其中baseOffset是该日志文件中第一条消息的offset。

在一个Segment里面,消息日志是追加写人的,如果满足日志文件或索引文件超过一定大小或者当前时间-文件创建时间大于规定的时间间隔(以上条件都是参数设置的),就会切分日志文件和索引文件,产生一个新的Segment,新的Segment用当前最新的Offset作为名称。第一个Segment存储的第一条消息的起始序号为0,因此文件名为20位长度的0来命名。

 将partition进一步细分为了若干的segment,每个segment文件的最大大小相等。

segment是一个逻辑概念,其由两类物理文件组成,分别为“.index”文件和“.log”文件。“.log”文件中存放的是消息,而“.index”文件中存放的是“.log”文件中消息的索引。

.log的文件名为当前该segment前有多少条消息,00000000000000170210.log 表示该segment中,当前文件前面有170210条消息:

4、 index和timeindex文件作用

从文件类型就可以看出是索引文件,其实就是为了加速读取log文件的速度

在单个partition中,存储的消息是有序的,每个消息被添加至分区时,以分区为单位顺序递增分配唯一offset来区别分区中每条不同的消息,offset也叫偏移量,是有序的数字,相当于消息的id,长度20位,不够20位的补0,它是消息在此分区中的唯一编号,Kafka保证在同一个分区内的消息是有序的,但是同一个topic中不同partition中消息是无序的。

首先:index和timeindex都是以相对偏移量的方式建立log消息日志的数据索引。比如说 0000.index和0550.index中记录的索引数字,都是从0开始的。表示相对日志文件起点的消息偏移量。而绝对的消息偏移量可以通过日志文件名 + 相对偏移量得到。

然后:这两个索引并不是对每一条消息都建立索引。而是Broker每写入40KB的数据,就建立一条index索引。由参数log.index.interval.bytes定制。
 

log.index.interval.bytes
The interval with which we add an entry to the offset index

Type:	int
Default:	4096 (4 kibibytes)
Valid Values:	[0,...]
Importance:	medium
Update Mode:	cluster-wide
5、Kafka文件清理机制

Kafka为了防止过多的日志文件给服务器带来过大的压力,他会定期删除过期的log文件。Kafka的删除机制涉及到几组配置属性:

5.1、如何判断哪些日志文件过期了
log.retention.check.interval.ms:定时检测文件是否过期。默认是 300000毫秒,也就是五分钟。
log.retention.hours , log.retention.minutes, log.retention.ms 。 这一组参数表示文件保留多长时间。默认生效的是log.retention.hours,默认值是168小时,也就是7天。如果设置了更高的时间精度,以时间精度最高的配置为准。
在检查文件是否超时时,是以每个.timeindex中最大的那一条记录为准。
5.2、过期的日志文件如何处理

log.cleanup.policy:日志清理策略。有两个选项,delete表示删除日志文件。 compact表示压缩日志文件。
当log.cleanup.policy选择delete时,还有一个参数可以选择。log.retention.bytes:表示所有日志文件的大小。当总的日志文件大小超过这个阈值后,就会删除最早的日志文件。默认是-1,表示无限大。

压缩日志文件虽然不会直接删除日志文件,但是会造成消息丢失。压缩的过程中会将key相同的日志进行压缩,只保留最后一条。

  • 2
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

w_t_y_y

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值