Kafka-集群架构设计

Kafka的Zookeeper元数据梳理

zookeeper整体数据

Kafka将状态信息保存在Zookeeper中,这些状态信息记录了每个Kafka的Broker服务与另外的Broker服务 有什么不同。通过这些差异化的功能,共同体现出集群化的业务能力。这些数据,需要在集群中各个Broker 之间达成共识,因此,需要存储在一个所有集群都能共同访问的第三方存储中。

Kafka的整体集群结构:

Kafka的集群中,最为主要的状态信息有两个:

  • 在多个Broker中,需要选举出一个Broker,担任 Controller角色。由Controller角色来管理整个集群中的分区和副本状态。

  • 在同一个Topic下的多个 Partition中,需要选举出一个Leader角色。由Leader角色的Partition来负责与客户端进行数据交互。

Zookeeper数据整体分布图:

Zookeeper客户端工具: prettyZoo。下载地址:Releases · vran-dev/PrettyZoo · GitHub

Controller Broker选举机制

在Kafka集群进行工作之前,需要选举出一个Broker来担任Controller角色,负责整体管理集群内的分区和副本状态。选举Controller的过程就是通过抢占Zookeeper的/controller节点来实现的。

当一个集群内的Kafka服务启动时,就会尝试往Zookeeper上创建一个/controller临时节点,并将自己的 brokerid写入这个节点。而Zookeeper会保证在一个集群中,只会有一个broker能够成功创建这个节点。这个注册成功的broker就成 了集群当中的Controller节点。节点内容:

{"version":2,"brokerid":0,"timestamp":"1702350416126","kraftControllerEpoch":-1}

临时节点:长时间断开连接,会被自动删除

监听机制:监听节点的状态,节点被删除后给所有监听器广播节点状态变化事件

Controller节点,负责监听Zookeeper中的其他一些关键节点,触发集群的相关管理工作:

  • 监听Zookeeper中的/brokers/ids节点,感知Broker增减变化。

  • 监听/brokers/topics,感知topic以及对应的partition的增减变化。

  • 监听/admin/delete_topic节点,处理删除topic的动作。

另外,Controller还需要负责将元数据推送给其他Broker。

Leader Partition选举机制

在Kafka中,一个Topic下的所有消息,是分开存储在不同的Partition中的。

使用kafka-topics.sh脚本创 建Topic时

  • 通过--partitions参数指定Topic下包含多少个Partition

  • 通过--replication-factors参数指定每个Partition有几个备份

在一个Partition的众多备份中,需要选举出一个Leader Partition,负责对接所有的客户端请求,并将消息优先保存,然后再通知其他Follower Partition来同步消息。

涉及的基础概念:

  • AR: Assigned Repllicas。 表示Kafka分区中的所有副本(存活的和不存活的)

  • ISR: 表示在所有AR中,服务正常且保持与Leader同步的Follower集合。如果Follower长时间没有向Leader发送通信请求(超时时间由replica.lag.time.max.ms参数设定,默认30S),那么这个Follower就会被踢出ISR。(在老版本的Kafka中,还会考虑Partition与Leader Partition之间同步的消息差值,大于参数replica.lag.max.messages条就会被移除ISR。现在版本已经移除了这个参数)

  • OSR:表示从ISR中踢出的节点。记录那些服务有问题,延迟过多的副本。

# 查看状态命令
bin/kafka-topics.sh -bootstrap-server localhost:9092 --describe --topic disTopic

在选举Leader Partition时,会按照AR中的排名顺序,靠前的优先选举。只要当前Partition在ISR列表中,也就是是存活的,那么这个节点就会被选举成为Leader Partition。(AR就是Replicas列中的Broker集合)

Leader Partition自动平衡机制

默认情况下,Kafka会尽量将Leader Partition分配到不同的Broker节点上,用以保证整个集群的性能压力能够比较平均。但是,经过Leader Partition选举后,这种平衡就有可能会被打破,让Leader Partition过多的集中到同一个Broker上,影响集群的整体性能。为此,Kafka设计了Leader Partition自动平衡机制,当发现Leader分配不均衡时,自动进行Leader Partition调整。

Leader Partition自平衡逻辑:会认为AR当中的第一个节点就应该是Leader节点。这种选举结果称为preferred election 理想选举结果。Controller会定期检测集群的Partition平衡情况,在开始检测时,Controller会依次检查所有的Broker。当发现这个Broker上的不平衡的Partition比例高于leader.imbalance.per.broker.percentage阈值时,就会触发一次Leader Partiton的自平衡。

官方文档的部分截图:

涉及Broker中server.properties配置文件的几个重要参数:

#1 自平衡开关。默认true
auto.leader.rebalance.enable
Enables auto leader balancing. A background thread checks the distribution of partition leaders at regular intervals, configurable by `leader.imbalance.check.interval.seconds`. If the leader imbalance exceeds `leader.imbalance.per.broker.percentage`, leader rebalance to the preferred leader for partitions is triggered.
Type:   boolean
Default:    true
Valid Values:   
Importance: high
Update Mode:    read-only
​
#2 自平衡扫描间隔
leader.imbalance.check.interval.seconds
The frequency with which the partition rebalance check is triggered by the controller
Type:   long
Default:    300
Valid Values:   [1,...]
Importance: high
Update Mode:    read-only
​
#3 自平衡触发比例
leader.imbalance.per.broker.percentage
The ratio of leader imbalance allowed per broker. The controller would trigger a leader balance if it goes above this value per broker. The value is specified in percentage.
Type:   int
Default:    10
Valid Values:   
Importance: high
Update Mode:    read-only

注意:使用集群时,要修改集群中所有broker的文件,并且重启Kafka服务才能生效

# 手动触发所有Topic的Leader Partition自平衡
bin/kafka-leader-election.sh --bootstrap-server worker1:9092 --election-type preferred  --topic secondTopic --partition 2

Leader Partition自平衡的过程是一个非常重的操作,因为要涉及到大量消息的转移与同步。并且,在这个过程中,会有丢消息的可能。所以在很多对性能要求比较高的线上环境,会选择将参数auto.leader.rebalance.enable设置为false,关闭Kafka的Leader Partition自平衡操作,用其他运维的方式,在业务不繁忙的时间段,手动进行Leader Partiton自平衡,尽量减少自平衡过程对业务的影响。

Partition故障恢复机制

当一组Partition中选举出了一个Leader节点后,这个Leader节点就会优先写入并保存Producer传递过来的消息,然后再同步给其他Follower。当Leader Partition所在的Broker服务发生宕机时,Kafka就会触发Leader Partition的重新选举。

Kafka为了消息能够在多个Parititon中保持数据同步,内部记录了两个关键数据:

  • LEO(Log End Offset): 每个Partition的最后一个Offset

每个Partition都会记录自己保存的消息偏移量。leader partition收到并记录了生产者发送的一条消息,就将LEO加1。follower partition从leader partition同步消息,每同步到一个消息,自己的LEO就加1。通过LEO值,就知道各个follower partition与leader partition之间的消息差距。

  • HW(High Watermark): 一组Partiton中最小的LEO。

follower partition每次往leader partition同步消息时,都会同步自己的LEO给leader partition。这样leader partition就可以计算出这个HW值,并最终会同步给各个follower partition。leader partition认为这个HW值以前的消息,都是在所有follower partition之间完成了同步的,是安全的。这些安全的消息可以被消费者拉取。而HW值之后的消息,是不安全的,可能丢失的。这些消息如果被消费者拉取消费了,就有可能造成数据不一致。

当服务出现故障时,如果是Follower发生故障,不会影响消息写入,只是少了一个备份而已。Kafka会做如下处理:

1、将故障的Follower节点临时踢出ISR集合。其他Leader和Follower继续正常接收消息。

2、出现故障的Follower节点恢复后,不会立即加入ISR集合。该Follower节点会读取本地记录的上一次的HW,将自己的日志中高于HW的部分信息全部删除掉,然后从HW开始,向Leader进行消息同步。

3、等到该Follower的LEO大于等于整个Partiton的HW后,就重新加入到ISR集合中。也就是说这个Follower的消息进度追上了Leader。

如果是Leader节点出现故障,Kafka为了保证消息的一致性,会做如下处理:

1、Leader发生故障,会从ISR中进行选举,将一个原本是Follower的Partition提升为新的Leader。这时,消息有可能没有完成同步,所以新的Leader的LEO会低于之前Leader的LEO。

2、Kafka中的消息都只能以Leader中的备份为准。其他Follower会将各自Log文件中高于HW的部分全部清理掉,然后从新的Leader中同步数据。

3、旧的Leader恢复后,将作为Follower节点,进行数据恢复。

在这个过程当中,Kafka注重的是保护多个副本之间的数据一致性。但是消息的安全性就得不到保障。

思考:HW和LEO是一个分布式的值,怎么保证HW在多个Broker中是一致的呢?

HW一致性保障-Epoch更新机制

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/245463.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

道路清障车行业分析:中国市场发展趋势研究

清障车全名为道路清障车,又称拖车、道路救援车、拖拽车,具有起吊、拽拉和托举牵引等多项功能,清障车主要用于道路故障车辆,城市违章车辆及抢险救援等。清障车按类别主要分为:拖吊连体型、拖吊分离型,一拖一…

leetcode---904. 水果成篮 -- 【滑动窗口/c++】

原题:904. 水果成篮 - 力扣(LeetCode) 题目解析: 本题中的fruit数组中的元素表示的是数的种类。如示例1,fruit【1,2,1】就表示下标0处有1号类型的树,下标1处有2号类型的树,下标2处有1号类型的…

智能优化算法应用:基于狮群算法3D无线传感器网络(WSN)覆盖优化 - 附代码

智能优化算法应用:基于狮群算法3D无线传感器网络(WSN)覆盖优化 - 附代码 文章目录 智能优化算法应用:基于狮群算法3D无线传感器网络(WSN)覆盖优化 - 附代码1.无线传感网络节点模型2.覆盖数学模型及分析3.狮群算法4.实验参数设定5.算法结果6.参考文献7.MA…

TSINGSEE青犀基于EasyCVR与AI技术的高校实验室视频可视化监管方案

一、行业背景 实验室作为科研、教学过程中的一个重要场所,其管理也十分至关重要。尤其是高校实验室安全问题,教育部《高等学校实验室安全规范》中说明,需要进一步加强高校实验室的安全管理工作,实现规范化、常态化的管理体制&…

C++ Qt开发:如何使用信号与槽

在Qt中,信号与槽(Signal and Slot)是一种用于对象之间通信的机制。是Qt框架引以为傲的一项机制,它带来了许多优势,使得Qt成为一个强大且灵活的开发框架之一。信号与槽的关联通过QObject::connect函数完成。这样的机制使…

【Linux】:线程(二)互斥

互斥与同步 一.线程的局部存储二.线程的分离三.互斥1.一些概念2.上锁3.锁的原理4.死锁 一.线程的局部存储 例子 可以看到全局变量是所有线程共享的,如果我们想要每个线程都单独访问g_val怎么办呢?其实我们可以在它前面加上__thread修饰。 这就相当于把g…

leetcode -- 209 长度最小的子数组[滑动窗口/c++]

原题链接:209. 长度最小的子数组 - 力扣(LeetCode) 算法原理: 滑动窗口其实就是同向双指针,因为计算结果的单调性,在符合条件的情况下,左右指针不必往回回溯,而实现优化的效果。 滑…

Python type函数:动态创建类

之前学习过使用 type() 函数可以查看变量的类型&#xff0c;但如果想使用 type() 直接查看某个类的类型呢&#xff1f;看如下程序&#xff1a; class Role:pass r Role() # 查看变量r的类型 print(type(r)) # <class __main__.Role> # 查看Role类本身的类型 print(type(…

SpringBoot之数组,集合,日期参数的详细解析

1.4 数组集合参数 数组集合参数的使用场景&#xff1a;在HTML的表单中&#xff0c;有一个表单项是支持多选的(复选框)&#xff0c;可以提交选择的多个值。 多个值是怎么提交的呢&#xff1f;其实多个值也是一个一个的提交。 后端程序接收上述多个值的方式有两种&#xff1a; 数…

打造绿色计算数智动力 HashData 入选“绿色计算最具价值解决方案”

12月13日-14日&#xff0c;由绿色计算产业联盟(GCC)、边缘计算产业联盟&#xff08;ECC&#xff09;联合举办“2023计算产业生态大会”&#xff08;CIEC 2023&#xff09;在北京举行。作为计算领域的权威会议&#xff0c;本次大会邀请了多位两院院士、众多产业专家&#xff0c;…

Python自动化测试系列[v1.0.0][多种数据驱动实现附源码]

前情提要 请确保已经熟练掌握元素定位的常用方法及基本支持&#xff0c;请参考Python自动化测试系列[v1.0.0][元素定位] 数据驱动测试是自动化测试中一种重要的设计模式&#xff0c;这种设计模式可以将测试数据和测试代码分开&#xff0c;实现数据与代码解耦&#xff0c;与此同…

C++随记

#include<bits/stdc.h> using namespace std; int main() { char* p "C Language"; cout<<p<<\n; cout<<p1<<\n; cout<<*p<<\n; cout<<*(p2)<<\n; } 随记 C Language Language C L 输出结果是p会输入整个字符…

【一秒梵高】基于OpenCV4实现图像九种风格迁移

风格迁移 图像风格迁移、色彩填充与色彩变换等&#xff0c;严格意义上来说都属于计算机视觉任务中图像处理的分支。它们输入的是图像&#xff0c;输出的也是图像&#xff0c;过程实现图像到图像的内容与风格的转换&#xff0c;深度学习在这类图像处理任务上也取得了良好的效果…

吴恩达深度学习L2W3作业

欢迎来到本周的编程作业。 到目前为止&#xff0c;你一直使用numpy来构建神经网络。现在&#xff0c;我们将引导你使用深度学习框架&#xff0c;该框架将使你可以更轻松地构建神经网络。TensorFlow&#xff0c;PaddlePaddle&#xff0c;Torch&#xff0c;Caffe&#xff0c;Kera…

小项目:迷宫

目录 引言1.题目描述及思想2.代码实现3.最终结果 引言 这个迷宫的话就是去年这时候&#xff0c;我记得当时讲这个的时候我还是一脸懵逼&#xff0c;就是事后花时间能够看懂&#xff0c;能够理解&#xff0c;但是自己肯定是不能够实现的&#xff0c;而且觉得这个东西非常的庞大…

一文讲清 QWidget 大小位置

一文讲清 QWidget 大小位置 前言 ​ QWidget 的位置基于桌面坐标系&#xff0c;以左上角为原点&#xff0c;向右x轴增加&#xff0c;向下y轴增加。 一、图解 ​ ​ 如上图所示&#xff0c;当窗口为顶层窗口时&#xff08;即没有任何父窗口&#xff09;&#xff0c;系统会自…

docker小白第三天

docker小白第三天 docker为什么会比虚拟机快 1、docker有着比虚拟机更少的抽象层。不需要Hypervisor实现硬件资源虚拟化&#xff0c;运行在docker容器上的程序直接使用的都是实际物理机的硬件资源&#xff0c;因此在CPU、内存利用率上docker将会在效率上有明显优势。 2、dock…

利用闭包与高阶函数实现缓存函数的创建

缓存函数是一种用于存储和重复利用计算结果的机制。其基本思想是&#xff0c;当一个函数被调用并计算出结果时&#xff0c;将该结果存储在某种数据结构中 (通常是一个缓存对象)以备将来使用。当相同的输入参数再次传递给函数时&#xff0c;不再执行实际的计算&#xff0c;而是直…

Unity 控制刚体的移动与旋转的方法

在场景创建一个Cube,并添加刚体&#xff0c;如图&#xff1a; 编写脚本&#xff1a; using System.Collections; using System.Collections.Generic; using UnityEngine;[RequireComponent(typeof(Rigidbody))] public class RibRotate : MonoBehaviour {//private Vector3 mo…

使用过滤器Filter实现请求拦截

早期使用servlet进行网络开发时&#xff0c;没有拦截器这些内容&#xff0c;那时做请求拦截都是使用Filter过滤器实现的&#xff0c;配置Filter要对哪些请求路径处理&#xff0c;有权限或不需要拦截的路径放行&#xff0c;没有权限的路径直接拦截请求。 一、Filter直接进行拦截…