1、什么是kafka?
Kafka是一种分布式的,基于发布/订阅的消息系统(消息队列)。
2、为什么要用kafka?
当业务逻辑变得复杂,数据量也会越来越多。此时可能需要增加多条数据线,每条数据线将收集到的数据导入到不同的存储和分析系统中。若仍使用之前的数据收集模式,则会出现以下问题:
1)生产者和消费者耦合度过高:当需要增加一个消费者时,所有的生产者都需要去改动,数据流水线扩展性差。
2)生产者消费者之间数据处理速率不对等:如果生产者的生产速率过高,可能会导致消费者压力过大,导致崩溃。
3)大量的并发网络连接对后台消费者不友好:大量生产者直接与消费者通信,对消费者造成过高的网络并发压力,会成为系统扩展中潜在的性能瓶颈;另外,大量并发生产者同时写入后端存储,可能会产生大量小文件,对Hadoop等分布式文件系统会造成存储压力。
分布式消息队列优点:降低耦合、异步执行、削峰填谷
3、kafka特点
1)高性能:相比于其他队列,Kafka拥有更高的性能和吞吐率。
2)良好的扩展性:采用分布式设计架构,数据经分片后写入多个节点,既可以突破单节点的存储处理的瓶颈,也可以实现高容错。
3)数据持久性:数据消息均会持久化到磁盘上,通过多副本避免数据丢失。采用顺序读写和批量写等机制,提高了磁盘操作效率。
4、kafka架构
Kafka采用了不同于其他队列push-push的架构,而是采用了push-pull架构。Producer直接将数据push给Broker,Consumer从Broker端pull数据。优势主要体现在以下两点:
1)Consumer可根据实际负载和需求获取数据,避免给Consumer带来太大压力。
2)Consumer自己维护已读消息的offset而不是由Broker维护,使Broker更加轻量级。
5、Producer
生产者,发布消息到Broker。
在Kafka中,每条数据被称为消息,每条消息表示为一个三元组:<topic, key, message>。
1)topic:表示该条消息所属的主题。topic是划分消息的逻辑概念,一个topic可以分布在多个Broker上。
2)key:表示该条消息的主键,Kafka会根据主键将同一topic下的消息划分为不同的分区。
当用户写入一条消息时,会对key求Hash值,用该数对partition数量求模,得到的就是分区编号,之后网络告知Broker,Broker写到对应的partition中。
3)message:表示该条消息的值,该数值的类型为字节数组,可以是普通的字符串、JSON对象,或者经序列化框架序列化过后的对象。
6、Broker
1)Kafka中Broker一般会有多个来组成分布式高容错集群。
2)Broker的主要职责是接受Producer和Consumer的请求,并把消息持久化到磁盘。
3)Broker以topic为单位将消息分成不同的分区,每个分区有多个副本,通过数据冗余方式实现容错。
4)当partition中存在多个副本时,其中一个为leader,对外提供读写请求,其余为follower,不对外提供读写请求,只是同步leader中的数据,当leader出现问题时,通过选举算法将其中一个选举为leader。
5)Broker能保证同一topic下的同一partition内数据有序,无法保证partition之间的数据全局有序。
6)Broker以追加的方式将数据写入磁盘,且每个分区中的消息被赋予了唯一整数标识,称为offset。
7)Broker中保存的数据是有有效期的,如果超过了有效期,将磁盘中的数据移除以释放空间,在有效期内,Consumer可以任意重复读取不受限制。
7、Consumer
消费者,主动从Broker中拉取消息进行处理。
1)Consumer自己维护最后一个已读消息的offset。
2)Kafka允许多个Consumer构成一个Consumer Group,共同读取一个topic中的数据来提高效率。
3)Kafka可以自动为同一Group中的Consumer分摊负载,从而实现消息的并发读取。
4)Kafka在某个Consumer发生故障时,自动将它处理的partition转移给同组的其它Consumer来处理。
8、Zookeeper
1)Broker与Zookeeper:Broker会向Zookeeper进行注册,将自己的位置、健康状态、维护的topic和partition等信息写入Zookeeper,以便于其它可以发现获取这些数据。
2)Consumer与Zookeeper:Consumer Group利用Zookeeper保证组内的Consumer负载均衡。
9、关键技术点
1)可控的可靠性级别
Producer可以通过两种方式向Broker发送数据,同步和异步。其中异步方式通过批处理方式大大提高了写入效率。不管是以何种方式,Producer均能通过消息应答方式,在写效率和可靠性之间(二者是此消彼长的)做一个较好的权衡。
目前支持三种消息应答方式,通过控制参数request.required.acks:
0:Produce向Broker发送消息后马上返回,无需等待写是否成功,效率最高但不能保证消息被成功接收且写入磁盘。
1:Produce向Broker发送消息后需要等待leader partition写入成功才会返回,不能保证follower partition写入成功,在相对高效的情况下保证至少写入成功一个节点。
-1:Produce向Broker发送消息后需要等待所有的partition写成功后才会返回,容错性高效率低,特别是在写入某个节点较慢时。
2)数据多副本
partition中存在多个副本其中一个为leader,对外提供读写请求,其余为follower,不对外提供读写请求,只是同步leader中的数据,当leader出现问题时,通过选举算法将其中一个选举为leader。
Kafka Broker的负载均衡实际上是对leader partition的负载均衡,保证leader partition在各个Broker上的数目尽可能相近。
3)高效的持久化机制
为了应对大数据的场景,Kafka Broker直接将数据写入磁盘而不是内存。
Kafka Broker利用顺序写的方式写入磁盘,并结合offset方式大大提高了写的效率。
4)数据优化传输
批处理:为了降低单条消息传输带来的网络开销,Broker将多条消息组装在一起。Kafka对数据格式进行统一设计,避免数据格式转换带来的开销。
zero-copy:通常情况下,从磁盘中读取数据并发送出去需要经过4次拷贝(内核态->用户态应用->内核态->网卡),两次系统调用。
通过zero-copy技术优化后,只需要经过3次拷贝(内核态->内核态->网卡),无需任何系统调用,大大提高发送效率。
可控的消息传递语义:
at most once:生产者在给消费者发送消息后就返回,这种情况下消费者可能成功接收到消息,也可能丢失。
at least once:生产者在给消费者发送消息后需要等待确认,如没确认则重新发送消息,这种情况下能保证消费者接收,但可能重复接收。
exactly once:消费者会且只会处理一次处理过的消息。
10、保证数据时序性
Broker能保证同一topic下的同一partition内数据有序,无法保证partition之间的数据全局有序。
1)所以应该把要保证时序性的数据放在同一partition内。
2)topic只有一个partition,保证了这个topic中所有数据有序。
内容来源书籍:《大数据技术体系详解 原理、架构与实践》 --董西成