美文网首页
kafka kafka生产者

kafka kafka生产者

作者: dylan丶QAQ | 来源:发表于2020-10-14 12:34 被阅读0次

起因:在实际项目开发过程中,需要使用RabbitMQ来实现消息队列的功能,在运用过之后,也去学一学kafka,了解一下他们之间的差别,吃一吃架构方面的相关内容,提升自己。


1. kafka生产者分析

1.1. 生产者分区的原则

为什么要分区

  • 提升了水平扩展能力

  • 提供并发能力

分区的原则

  • 指明partition的情况下,直降将指明的值作为partition的值(指定存放分区)

  • 没有指明partition,但有key的情况下,会将key的hash值与topic的partition数量进行取余得到partition值

  • 什么都没有指定,在第一发消息的时候,系统会随机生成一个整数来对topic的partition数量进行取余得到partition值,后面每次都对这个已经生成的随机数进行+1,这就得到了round-robin算法了

1.2. Kafka副本的复制方案

1.2.1. 副本的复制方式分析

Kafka内部发送响应的机制:为了保证producer的数据能够可靠的发送并保存到topic上,topic的每个partition收到发送的数据后,都需要向生产者发送ACK,如果生产者收到ACK,就会进行下一轮发送,如果没有收到就会重新发送

副本的复制是如何复制的?

Producer--->leader(follower1,follower2)

这个情况下应该如何向Producer发送ACK

方案一:确保半数以上的follower完成同步,就发送ACK,优点是延迟低,在选举新的leader的时候,如果容忍n台节点故障,就需要2n+1个副本

方案二:完成全部follower的同步,才发送ACK,缺点是延迟高,在选举新的leader的时候,如果容忍n台节点故障,只就需要n+1个副本

kafka使用方案二作为follower的同步方式

  • 如果选择方案一:虽然网络延迟低,但数据一致性无法保障,而且需要2n+1个副本,副本过多就会导致数据冗余过大,造成很大浪费

  • 虽然方案二延迟高,但对于kafka来说影响不大

1.2.2. 通过ISR优化副本同步

先看一下topic的详细信息

Topic: topicfirst       PartitionCount: 5       ReplicationFactor: 1    Configs: 
Topic: topicfirst       Partition: 0    Leader: 11      Replicas: 11    Isr: 11
Topic: topicfirst       Partition: 1    Leader: 11      Replicas: 11    Isr: 11
Topic: topicfirst       Partition: 2    Leader: 11      Replicas: 11    Isr: 11
Topic: topicfirst       Partition: 3    Leader: 11      Replicas: 11    Isr: 11
Topic: topicfirst       Partition: 4    Leader: 11      Replicas: 11    Isr: 11

在kafka采用第二种方案进行副本复制后进行ACK响应,会等待所有follower完成同步,这个时候如果有一个follower因为某种原因无法访问,这个时候leader就要一直等着这个follower来完成同步才能发ACK给producer

Kafka的解决方案:Leader维护了一个动态的in-sync replica set(ISR)

  • 副本同步机制

    • 作用是和leader保持同步的follower集合

    • 当ISR中的follower完成数据同步之后,leader就会给follower发送ack(数据是由folloer主动从leader那里拉取过来的)

  • ISR是一个动态同步集合:从ISR中移除follower的条件是当follower长时间未向leader拉取数据,该follower就会被剔除出ISR,时间阀值由:replica.lag.time.max.ms=10000 决定 单位ms

    replica.lag.max.messages 这个是leader和follower的消息数的差,超过就剔除出ISR,这个参数在0.9版本已经移除

  • 当leader发生故障了,就会从ISR中选举新leader

2. Kafka生产者的ACK机制(可靠性)

ACK(在rabbitmq里面,我们producer和broker的一个反馈是什么?callback,return)

对于kafka不太重要的数据是不是就不需要可靠性很高了

副本机制 主分片--副本分片

producer发送给broker-->partition(leader)-->replication(2)

这个时候,我们思考一个生产者的ACK机制,p roducer通过一个配置项目ACKS

  • acks = 0 : producer只要给到broker就返回ack,当broker接收到数据后,如果broker故障导致数据丢失

  • acks =1 : partition的leader落盘成功后才返回ACK,不关心follower,当我们的partition的leader挂掉后数据就无法同步到follower(leader挂了,要选举生成新的leader)

  • acks = -1 : 所有ISR中的分区都同步成功才会返回ACK给producer

kafka的producer在没有接收到ACK后会重试,这个重试是有次数的,这个次数是你配置的

3. Kafka分布式保存数据一致性问题

producer有一个重试机制,如果数据没有接收到ACK的情况下,重新再次发送

场景分析:如果有一个leader,两个follower,当leader宕机了

[图片上传失败...(image-655708-1602662879949)]

LEO(Log End Offset):每个副本最后一个offset

HW(High Watermark):所有副本中最小的那个LEO(7)

数据一致性的执行细节:

1、follower故障

follower发生故障就会被剔除出ISR,待follower恢复后,follower会读取本次磁盘上上次记录的HW(7),将log文件中高于HW部分截取掉,从HW开始向leader进行同步,待follower的LEO大于等于Partition副本的HW,当follower追上leader以后,就可以重入ISR

2、leader故障

leader故障之后,会从ISR中选一个follower成为leader,为保证多个副本间的数据一致,将所有的副本各自的高于HW的数据部分截取掉,从新的leader同步数据

注意:这个只能保证数据一致性,不能保证数据不丢失或者不重复

4. Kafka的Exactly Once实现

将producer的ack设置为-1,保证数据producer到partitons的数据不丢失,就是At Least Once,如果将ack设置为0,可以保证每条消息只会发送一次,即At Most Once

At Least Once可以保证数据不丢失,但不能保证数据不重复,At Most Once可以保证数据不重复,但不能保证数据不丢失

Exactly Once = At Least Once + 幂等性

At Least Once 可以通过Producer的ACKS设置为-1来解决,在kafka的v0.11(含)之后引入了一个新特性:producer端的幂等性,无论Producer发给broker多少次,只要数据重复,broker只会持久化一条给到topic

在Producer端通过参数 enable.idempotence 设置为true即可,相当于开起了producer端的幂等性:Producer在初始化的时候会被分配一个PID,发往同一个Partition的消息会附带Sequence Number。broker端会对

<PID,Partition,Sequence Number>做主键缓存,当有相同主键信息只会持久化一条了

但是:系统只要重启就会更新PID,在不同的Partition上会有不同的主键,所以Producer的幂等无法保证跨分区跨会话的Exactly Once

5. Kafka生产者的事务机制

kafka的数据可以有很多的partition

场景:当producer个p0,p1,p2写入数据,0-10,1-15,正要给2分区写数据broker挂了,如果acks=1,有主分区没有写入完成,producer会重试发送

在kafka的v0.11版本引入了transactionID,将transactionID和PID绑定并保存事务状态到一个内部的topic中,当服务重启后该事务状态还能获取

6. Kafka发送消息的流程

kafka的producer发送消息采用的是异步发送模式,一个main一个sender还有一个线程共享变量(RecordAccumulator)

[图片上传失败...(image-4ad6e3-1602662879948)]

batch.size : 数据积累到多大以后,sender才会发送

linger.ms : 如果一直没有达到batch.size,sender会等待linger.ms时间后就发送


不要以为每天把功能完成了就行了,这种思想是要不得的,互勉~!

相关文章

  • 【Kafka】Kafka 常用命令

    本篇结构: kafka topic 管理脚本 kafka 生产者控制台 kafka 消费者控制台 kafka 消费...

  • kafka0.8

    1、Kafka分为:生产者(producer),消费者(consumer) 2、生产者提交消息,给Kafka集群,...

  • 使用pykafka库测试kafka-180504-[github

    使用pykafka库测试kafka 生产者生产数据 在kafka目录下执行./kafka-console-cons...

  • Kafka中概念的简单汇总

    (1)Producer:Kafka生产者,负责往Kafka写数据的客户端;(2)Consumer: Kafka消费...

  • Kafka - 生产者初步学习

    Kafka - 生产者初步学习 一、kafka生产者组件 我们从创建一个 ProducerRecord 对象开始,...

  • kafka使用

    框架: spring-kafka 1.2.2 生产者端代码 说明: bootstrapServers: kafka...

  • Kafka常用命令

    启动Kafka并生产消费消息 启动ZooKeeper 启动Kafka 查看启动后kafka的版本 生产者发送消息 ...

  • Kafka生产者:写消息到Kafka

    本章我们将会讨论Kafka生产者是如何发送消息到Kafka的。Kafka项目有一个生产者客户端,我们可以通过这个客...

  • [kafka系列]之producer端消息发送

    本小节我们来讨论Kafka生产者是如何发送消息到Kafka的, Kafka项目有一个生产者客户端,我们可以通过这个...

  • Kafka生产者:写消息到Kafka

    本章我们将会讨论Kafka生产者是如何发送消息到Kafka的。Kafka项目有一个生产者客户端,我们可以通过这个客...

网友评论

      本文标题:kafka kafka生产者

      本文链接:https://www.haomeiwen.com/subject/ljrwpktx.html