Kafka基础

 

目录

1、架构图

2、再均衡

3、编码

4、相关问题


1、架构图

一个topic的多个partition(每个partition有多个副本)

topic:Kafka对消息进行归类,发送到集群的每一条消息都要指定一个topic

partition:物理上的概念,每个topic包含一个或多个partition,一个partition对应一个文件夹,这个文件夹下存储partition的数据和索引文件,每个partition内部是有序的。每个partition在存储层面是一个append log文件,发布到此partition的消息会追加到log文件的尾部,为顺序写人磁盘(顺序写磁盘比随机写内存的效率还要高)。每条消息在log文件中的位置成为offset(偏移量),offset为一个long型数字,唯一标记一条消息。(00000.kafka、00001.kafka、00002.kafka)kafka中只能保证partition中记录是有序的,而不保证topic中不同partition的顺序。

副本:leader和follower都称为副本,一个partition有多个副本,这些副本中只有一个leader副本,其余都为follower副本。消费者和生产者只与leader副本进行交互。follower实时地从 leader 中同步数据,保持和 leader 数据的同步。leader 发生故障时,某个 follower 会成为新的 leader(选举新leader采用raft算法

producer:生产者,产生消息

comsumer:消费者,拉取消息

消费组:每个Consumer属于一个特定的Consumer Group(可为每个Consumer指定group name,若不指定group name则属于默认的group)。同一个组内的consumer是竞争关系来消费消息(一条消息只会被一个组内的一个consumer消费)。

2、再均衡

在Kafka中,当有新消费者加入或者订阅的topic数发生变化时,会触发Rebalance(再均衡:在同一个消费者组当中,分区的所有权从一个消费者转移到另外一个消费者)机制,Rebalance顾名思义就是重新均衡消费者消费。Rebalance的过程如下:

  1. 所有成员都向coordinator发送请求,请求入组。一旦所有成员都发送了请求,coordinator会从中选择一个consumer担任leader的角色,并把组成员信息以及订阅信息发给leader
  2. leader开始分配消费方案,指明具体哪个consumer负责消费哪些topic的哪些partition。一旦完成分配,leader会将这个方案发给coordinator。coordinator接收到分配方案之后会把方案发给各个consumer,这样组内的所有成员就都知道自己应该消费哪些分区了。所以对于Rebalance来说,Coordinator起着至关重要的作用

3、编码

创建生产者:

Properties kafkaProps = new Properties();
kafkaProps.put("bootstrap.servers", "broker1:port1, broker2:port2");
kafkaProps.put("key.serializer", "org.apache.kafka.common.StringSerializer");
kafkaProps.put("value.serializer", "org.apache.kafka.common.StringSerializer");
producer = new KafkaProducer<String, String>(kafkaProps);

Kafka的生产者有如下三个必选的属性:

  • bootstrap.servers,指定broker的地址清单
  • key.serializer必须是一个实现org.apache.kafka.common.serialization.Serializer接口的类,将key序列化成字节数组。注意:key.serializer必须被设置,即使消息中没有指定key。
  • value.serializer,将value序列化成字节数组

发消息:

同步:

ProducerRecord<String, String> record = new ProducerRecord<>("CustomCountry", "Precision Products", "France");//Topic Key Value
try{
    Future future = producer.send(record); 
    future.get();//不关心是否发送成功,则不需要这行。
} catch(Exception e) {
    e.printStackTrace();//连接错误、No Leader错误都可以通过重试解决;消息太大这类错误kafkaProducer不会进行任何重试,直接抛出异常
} 

异步:

ProducerRecord<String, String> record = new ProducerRecord<>("CustomCountry", "Precision Products", "France");//Topic Key Value
producer.send(record, new DemoProducerCallback());//发送消息时,传递一个回调对象,该回调对象必须实现org.apahce.kafka.clients.producer.Callback接口

private class DemoProducerCallback implements Callback {
    @Override
    public void onCompletion(RecordMetadata recordMetadata, Exception e) {
        if (e != null) {//如果Kafka返回一个错误,onCompletion方法抛出一个non null异常。
            e.printStackTrace();//对异常进行一些处理,这里只是简单打印出来
        }
    }
} 

消费指定分区:

TopicPartition topicPartition = new TopicPartition("test" , 1);
KafkaConsumer consumer = new KafkaConsumer(props);
consumer.assign(Arrays.asList(topicPartition));

4、相关问题

kafka消息如何保证顺序:

原因:数据库中的binlog;一些业务需要,比如希望把某个订单的数据写入一个partion

为何消息会错乱:由于消费者消费消息之后,消费之后,有可能交给很多个线程去处理数据(如下图),这样就导致数据顺序错乱

kafka特点:kafka中,写入一个partion照片中的数据是一定有顺序的;kafka中一个消费者消费一个partion的数据,消费者取出数据时,也是有顺序的。为了保证一个消费者中多个线程去处理时,不会使得消息的顺序被打乱,则可以在消费者中,消息分发至不同的线程时,加一个队列,消费者去做hash分发,将需要放在一起的数据,分发至同一个队列中,最后多个线程从队列中取数据,如下图所示。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值