Kafka05:Kafka的存储和容错机制:存储策略、容错机制

12 篇文章 1 订阅

一、存储策略

在kafka中每个topic包含1到多个partition,每个partition存储一部分Message。每条Message包含三个属性,其中有一个是offset。

问题来了:offset相当于partition中这个message的唯一id,那么如何通过id高效的找到message?

两大法宝:分段+索引

kafak中数据的存储方式是这样的:
1、每个partition由多个segment【片段】组成,每个segment中存储多条消息,
2、每个partition在内存中对应一个index,记录每个segment中的第一条消息偏移量。

Kafka中数据的存储流程是这样的:
生产者生产的消息会被发送到topic的多个partition上,topic收到消息后往对应partition的最后一个segment上添加该消息,segment达到一定的大小后会创建新的segment。

来看这个图,可以认为是针对topic中某个partition的描述。

在这里插入图片描述
图中左侧就是索引,右边是segment文件,左边的索引里面会存储每一个segment文件中第一条消息的偏移量,由于消息的偏移量都是递增的,这样后期查找起来就方便了,先到索引中判断数据在哪个segment文件中,然后就可以直接定位到具体的segment文件了,这样再找具体的那一条数据就很快了,因为都是有序的。

二、容错机制

1、一个Broker节点宕机

当Kafka集群中的一个Broker节点宕机,会出现什么现象?

下面来演示一下
使用kill -9 杀掉bigdata01中的broker进程测试。

[root@bigdata01 kafka_2.12-2.4.1]# jps
7522 Jps
2054 Kafka
1679 QuorumPeerMain
[root@bigdata01 kafka_2.12-2.4.1]# kill 2054

我们可以先通过zookeeper来查看一下,因为当kafka集群中的broker节点启动之后,会自动向zookeeper中进行注册,保存当前节点信息。

[root@bigdata01 apache-zookeeper-3.5.8-bin]# bin/zkCli.sh 
Connecting to localhost:2181
.....
[zk: localhost:2181(CONNECTED) 1] ls /brokers
[ids, seqid, topics]
[zk: localhost:2181(CONNECTED) 2] ls /brokers/ids
[1, 2]

此时发现zookeeper的/brokers/ids下面只有2个节点信息。

可以通过get命令查看节点信息,这里面会显示对应的主机名和端口号。

[zk: localhost:2181(CONNECTED) 4] get /brokers/ids/1
{"listener_security_protocol_map":{"PLAINTEXT":"PLAINTEXT"},"endpoints":["PLAINTEXT://bigdata02:9092"],"jmx_port":-1,"host":"bigdata02","timestamp":"1591668875280","port":9092,"version":4}

然后再使用describe查询topic的详细信息,会发现此时的分区的leader全部变成了目前存活的另外两个节点。

此时可以发现Isr中的内容和Replicas中的不一样了,因为Isr中显示的是目前正常运行的节点。

所以当Kafka集群中的一个Broker节点宕机之后,对整个集群而言没有什么特别的大影响,此时集群会给partition重新选出来一些新的Leader节点。

[root@bigdata01 kafka_2.12-2.4.1]# bin/kafka-topics.sh --describe --zookeeper localhost:2181 --topic hello                       
Topic: hello    PartitionCount: 5       ReplicationFactor: 2    Configs: 
        Topic: hello    Partition: 0    Leader: 2       Replicas: 2,0       Isr: 2
        Topic: hello    Partition: 1    Leader: 1       Replicas: 0,1       Isr: 1
        Topic: hello    Partition: 2    Leader: 1       Replicas: 1,2       Isr: 1,2
        Topic: hello    Partition: 3    Leader: 2       Replicas: 2,1       Isr: 2,1
        Topic: hello    Partition: 4    Leader: 2       Replicas: 0,2       Isr: 2

2、新增一个Broker节点

当Kafka集群中新增一个Broker节点,会出现什么现象?

新加入一个broker节点,zookeeper会自动识别并在适当的机会选择此节点提供服务
再次启动bigdata01节点中的broker进程测试。

[root@bigdata01 kafka_2.12-2.4.1]# bin/kafka-server-start.sh -daemon config/server.properties

此时到zookeeper中查看一下。

[root@bigdata01 apache-zookeeper-3.5.8-bin]# bin/zkCli.sh 
Connecting to localhost:2181
.....
[zk: localhost:2181(CONNECTED) 1] ls /brokers
[ids, seqid, topics]
[zk: localhost:2181(CONNECTED) 2] ls /brokers/ids
[0, 1, 2]

发现broker.id为0的这个节点信息也有了。

在通过describe查看topic的描述信息,Isr中的信息和Replicas中的内容是一样的了。

[root@bigdata01 kafka_2.12-2.4.1]# bin/kafka-topics.sh --describe --zookeeper localhost:2181 --topic hello
Topic: hello    PartitionCount: 5       ReplicationFactor: 2    Configs: 
        Topic: hello    Partition: 0    Leader: 2       Replicas: 2,0       Isr: 2,0
        Topic: hello    Partition: 1    Leader: 1       Replicas: 0,1       Isr: 1,0
        Topic: hello    Partition: 2    Leader: 1       Replicas: 1,2       Isr: 1,2
        Topic: hello    Partition: 3    Leader: 2       Replicas: 2,1       Isr: 2,1
        Topic: hello    Partition: 4    Leader: 2       Replicas: 0,2       Isr: 2,0

但是启动后有个问题:发现新启动的这个节点不会是任何分区的leader?怎么重新均匀分配呢?

1、Broker中的自动均衡策略(默认已经有)

auto.leader.rebalance.enable=true
leader.imbalance.check.interval.seconds 默认值:300

2、手动执行:

bin/kafka-leader-election.sh --bootstrap-server localhost:9092 --election-type preferred --all-topic-partitions

我们尝试使用手工执行

[root@bigdata01 kafka_2.12-2.4.1]# bin/kafka-leader-election.sh --bootstrap-server localhost:9092 --election-type preferred --all-topic-partitions 
Successfully completed leader election (PREFERRED) for partitions hello-4, hello-1

执行后的效果如下,这样就实现了均匀分配。

[root@bigdata01 kafka_2.12-2.4.1]# bin/kafka-topics.sh --describe --zookeeper localhost:2181 --topic hello                         
Topic: hello    PartitionCount: 5       ReplicationFactor: 2    Configs: 
        Topic: hello    Partition: 0    Leader: 2       Replicas: 2,0Isr: 2,0
        Topic: hello    Partition: 1    Leader: 0       Replicas: 0,1Isr: 1,0
        Topic: hello    Partition: 2    Leader: 1       Replicas: 1,2Isr: 1,2
        Topic: hello    Partition: 3    Leader: 2       Replicas: 2,1Isr: 2,1
        Topic: hello    Partition: 4    Leader: 0       Replicas: 0,2Isr: 2,0

总结

写到这里也结束了,在文章最后放上一个小小的福利,以下为小编自己在学习过程中整理出的一个关于 java开发 的学习思路及方向。从事互联网开发,最主要的是要学好技术,而学习技术是一条慢长而艰苦的道路,不能靠一时激情,也不是熬几天几夜就能学好的,必须养成平时努力学习的习惯,更加需要准确的学习方向达到有效的学习效果。

由于内容较多就只放上一个大概的大纲,需要更及详细的学习思维导图的 点击我的Gitee获取
还有 高级java全套视频教程 java进阶架构师 视频+资料+代码+面试题!

全方面的java进阶实践技术资料,并且还有技术大牛一起讨论交流解决问题。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值