Topic&Partition

kafka topic权限管理 kafka topic not present_kafka

集群:在每个Kafka的节点配置中配置 zookeeper.connect=IP:2181,IP:2181,IP:2181/kafka

Topic:相当于数据库中的表,每个Topic 可以有多个Partition 以及副本ReplicationFactor

Partition:相当于每个大表的分表,一个Partition只能由同一Group 的单个Consumer消费,一个Partition存在多个Consumer 只有一个Consumer能消费数据

ReplicationFactor:每个Partition的副本

Offset:在data中会保存 数据log、indexlog、timestamplog;

①通过当前offset,去indexlog中找到offset对应的position在数据log中的字节位置

②通过时间戳 ,去timestamplog中找到对应的offset位置 再重复上面操作

kafka topic权限管理 kafka topic not present_kafka_02

生产者

kafka topic权限管理 kafka topic not present_kafka_03

生产者代码(源码)

public static String brokers = "node01:9092,node02:9092,node03:9092";
public static Properties initConf(){
    Properties conf = new Properties();
    conf.setProperty(ProducerConfig.ACKS_CONFIG,"0");
    conf.setProperty(ProducerConfig.KEY_SERIALIZER_CLASS_CONFIG, StringSerializer.class.getName()); //key得序列话
    conf.setProperty(ProducerConfig.VALUE_SERIALIZER_CLASS_CONFIG,StringSerializer.class.getName());//value得序列话
    conf.setProperty(ProducerConfig.BOOTSTRAP_SERVERS_CONFIG,brokers);                              //集群
    conf.setProperty(ProducerConfig.PARTITIONER_CLASS_CONFIG, DefaultPartitioner.class.getName());
    conf.setProperty(ProducerConfig.BATCH_SIZE_CONFIG,"16384"); //16k 要调整的,分析我们msg的大小,尽量触发批次发送,减少内存碎片,和系统调用的复杂度
    conf.setProperty(ProducerConfig.LINGER_MS_CONFIG,"0");  //
    conf.setProperty(ProducerConfig.MAX_REQUEST_SIZE_CONFIG,"1048576");                             //一个批次最大 (batch累加不可超过)
    //message.max.bytes
    conf.setProperty(ProducerConfig.BUFFER_MEMORY_CONFIG,"33554432");//32M                          //所有分区 所有batch的大小
    conf.setProperty(ProducerConfig.MAX_BLOCK_MS_CONFIG,"60000"); //60秒
    conf.setProperty(ProducerConfig.MAX_IN_FLIGHT_REQUESTS_PER_CONNECTION,"5");
    conf.setProperty(ProducerConfig.SEND_BUFFER_CONFIG,"32768");  //32K   -1                       //单次发送大小
    conf.setProperty(ProducerConfig.RECEIVE_BUFFER_CONFIG,"32768"); //32k  -1
    return conf;
}
Properties conf = initConf();
KafkaProducer<String, String> producer = new KafkaProducer<>(conf);

while (true) {
    ProducerRecord<String, String> msg = new ProducerRecord<String, String>("ooxx", "hello", "ooxx1");

    Future<RecordMetadata> future = producer.send(msg);
    RecordMetadata recordMetadata = future.get();

}

首先new KafkaProducer对象 初始化

  • RecordAccumulator 纪录累加器

每个Topic的分区为单位

  • ②new Sender

当new KafkaProducer对象就会起一个线程 死循环去RecordAccumulator 纪录累加器取数据真正的send到磁盘中

该类是实现了Runnable

  • ③new KafkaThread(ioThreadName, this.sender, true);

启动线程实现Sender的方法

调用send方法 (RecordAccumulator.append)

  • key、value序列号
  • 计算分区:ProducerRecord生产数据时要有topic key value,其中key通过partitioner.partition()方法计算出所在分区,key为null时:在目前可用分区中通过count累加取余数算出partition ;key不为null时:通过所有分区Hash取余数算出partition。
  • accumulator.append() 往RecordAccumulator 纪录累加器中append()

通过所在分区,往Batch为实体的双端队列中(Deque<RecordBatch> ) append ,使用synchronized避免并发问题。

RecordBatch配置BATCH_SIZE_CONFI该参数:当生产的数据大小 小于该配置时,使用系统提前分配好的内存空间往batch塞数据,当大于时 系统会阻塞分配内存空间至新的batch(该大小合理分配 不会阻塞,且不易产生碎片问题)

IOthread:Sender(待完善)

  • 死循环去RecordAccumulator 纪录累加器取数据真正的send到磁盘中
  • accumulator.ready()每个双端队列Deque中,是否超时,或者超过batch批次大小

LINGER_MS_CONFIG:配置时间,当超过这个时间触发一次,send到磁盘中

MAX_REQUEST_SIZE_CONFIG:配置批次大小,超过 则send到磁盘中

 

ACK

0:生产消息时,直接往Kafka中丢数据,不返回offset值

1(默认):生产消息时,往Kafka中丢数据,成功往某个Topic的partition中send数据后 返回offset值

-1(All):(分布式)生产消息时,往Kafka中丢数据,成功往某个Topic的partition中send数据后 返回offset值,并且等副本ReplicationFactor同步该数据后返回offset值

kafka topic权限管理 kafka topic not present_IP_04

ISR:

kafka topic权限管理 kafka topic not present_IP_05

OSR:

kafka topic权限管理 kafka topic not present_数据_06

AR:

kafka topic权限管理 kafka topic not present_内存空间_07