一、Kafka 的定义
百度百科是这样定义 Kafka 的:
Kafka 是由 Apache 软件基金会开发的一个开源流处理平台,由 Scala 和 Java 编写。Kafka 是一种高吞吐量的分布式发布订阅消息系统,它可以处理消费者在网站中的所有动作流数据
Kafka 官网是这样定义自己的:
Apache Kafka 是一个开源分布式事件流平台,被数千家公司用于高性能数据管道、流分析、数据集成和关键任务应用程序
我们扩展总结一下:
- 作为消息队列:Kafka 是一个分布式、支持分区的、多副本的分布式消息系统,可以建立实时流数据管道,以可靠地在系统或应用程序之间获取数据,相比较于其他消息队列,其设计中大量使用了批量处理和异步的思想,最高可以每秒处理千万级别的消息
- 作为流式处理平台: Kafka 为流行的流式处理框架提供了可靠的数据来源,还提供了一个完整的流式处理框架,比如窗口、连接、变换和聚合等各类操作;在大数据和流计算领域,Kafka 与周边生态系统的兼容性是最好的没有之一
二、Kafka 的应用场景
Kafka 被广泛应用于两大场景:
- 消息队列:建立实时流数据管道,以可靠地在系统或应用程序之间获取数据
- 数据处理:构建实时的流数据处理程序来转换或处理数据流
1. 消息队列
传统的消息队列应用场景无非就那几种:缓存/削峰、解耦和异步通信。
1)缓存/削峰
有些场景如秒杀、放号,都有一个明显的特点,就是在短时间内,会有大量的数据流冲向系统,有可能超过系统的处理极限,从而导致系统崩溃,不可用。引入 Kafka 作为消息队列,可以将消息先写入 Kafka,控制和优化数据流入系统的速度。
图自:尚硅谷
2)解耦
打个比方,在使用 RPC 来进行上下游系统调用的情况下,如订单系统和库存系统,如果库存系统挂掉,订单系统会跟着一起躺,如果需要增加一个下游系统,那么订单系统需要跟着改核心逻辑。
引入 Kafka 作为消息队列后,订单系统不再直接通知下游系统,而是将消息发往队列,由下游系统自行拉取消息,从而实现系统之间的解耦,,解耦后允许你独立的修改生产和消费的逻辑,互不影响。
3)异步通信
将一些与核心业务逻辑关系不大的模块抽出来,放入消息队列,这样能保证核心业务不受影响,减少等待时间。
图自:尚硅谷
2. 流处理
Kafka 保存收集流数据,以提供之后对接的流式计算框架进行处理。
图自:博客
三、Kafka 的基础架构
消息队列有两种模型:
- 点对点模型,消费者主动拉取消息,收到消息后清除队列里的消息
- 发布订阅模型,使用主题作为消息的通信载体,类似于广播,消费者收到消息后不删除数据,每个消费者之间互相独立,都可以消费到数据
Kafka 采用的是发布 - 订阅模型。下图可以很好的表述 Kafka 的整个基础架构,图自:尚硅谷。
上图出现的概念要搞清楚:
- Producer(生产者) :消息的生产方
- Consumer(消费者) :消息的消费方
- Group(消费组) :每个消费者都会有一个 GroupId ,GroupId 相等的话代表他们属于同一个 Group,一个 GroupId 可以看做是一个消费者,它们不会重复的消费同一条消息
- Broker(代理) :对于 Broker 可以简单理解为一个独立的 Kafka 实例 , 通过分布式架构,Kafka 集群可以横向扩容很多的 Broker ,以增加自己的并发处理能力
- Topic(主题) : Producer 将消息发送到特定的主题,Consumer 通过订阅特定的 Topic(主题) 来消费消息
- Partition(分区) :Partition 属于 Topic 的一部分。一个 Topic 可以有多个 Partition ,并且同一 Topic 下的 Partition 可以分布在不同的 Broker 上,这也就表明一个 Topic 可以横跨多个 Broker ,但是 Partition 不会跨越 Broker
- Offset(消息在 Partition 的偏移量) :消息被追加到 Partition 时都会被分配一个 Offset ,Partition 会维护每个 GroupId 的 Offset ,也就是记录不同消费组消费的位置,尽管一个消费组有多个消费者,但它们只能按顺序的消费这个 Partition 中的消息,而不会重复消费
- Replica(副本) :每个 Partition 都有若干个副本,一个 Leader 和若干个 Follower,主从机制,平时只跟 Leader 打交道,Follower 只负责备份
Kafka 的基础架构并不难以理解,只要把这个搞清楚,Kafka 的上手难度将成级数下降!
四、多副本机制
Kafka 为了提高消息存储的安全性和容灾能力,引入了多副本机制。
多副本机制是针对 Partition 设计的,可以这么理解,Kafka 为 Partition 拷贝了多份,并且这个份数是可以指定的,多份 Partition 中属于主从关系,只有一个 Leader,其他叫 Follower,当 Leader 不行了,挂了,会从所有Follower中挑一个合格的上位,与 Leader 同步程度达不到要求的都是不够资格的小弟,不参加 Leader 选举。
我们平时其实只跟 Leader 打交道,发送的消息都在 Leader 中,消息提交到 Leader 后其他 Follower 会自动从 Leader 中拉取同步。
1. Leader 选举原理
我们先来了解一个概念:ISR(In-sync Replicas)同步的副本集合,在这个集合内的副本被认为是完全同步的,包括 Leader 也存在于这个集合中。
Broker 有一个参数叫 replica.lag.time.max.ms,用于控制 Follower 能落后 Leader 多少时间,落后不超过这个时间的副本 Kafka 就认为它是同步的,落后超过这个时间该 Follower 会从 ISR 中踢出。
若是 Leader 挂了,集合也空了,这个分区就不可用了,因此,生产环境中,合理的配置副本也是非常重要的一项。
2. 选举规则
- ISR 不为空,直接从 ISR 中选举
- ISR 为空,Kafka 也可以从不在 ISR 中的存活副本中选举,这个过程称为 Unclean 领导者选举
对于第二个选项,可以通过 Broker 端的 unclean.leader.election.enable 参数来控制。
开启 Unclean 领导者选举可能会造成数据丢失,但好处是,它使得分区 Leader 副本一直存在,不至于停止对外提供服务,因此提升了高可用性,不推荐,毕竟可用性可以通过其他手段来提升。
反之,禁止 Unclean 领导者选举的好处在于维护了数据的一致性,避免了消息丢失,但牺牲了高可用性。
五、写在最后
Kafka 专栏已经更新了四期啦:
- 本期:「Kafka 专栏」- 001 Kafka 概述
- 「Kafka 专栏」- 002 Kafka 生产者详解
- 「Kafka专栏」- 003 生产者常用的调优手段
- 「Kafka专栏」- 004 Kafka 分区机制详解
本系列长期更新,内容根据资料整理和个人理解重新整理输出,原创保证。我是蛋糕,致力于以体系化的方式分享知识,点个关注不迷路!