kafka入门与基础使用

kafka核心介绍(版本:kafka_2.11-2.0.0.tgz)

(1)消息中间件(MQ)
--异步调用
同步变异步
--应用解耦
提供基于数据的接口层
--流量削峰
缓解瞬时高流量压力
(2)消息中间件的术语
Broker:消息服务器,提供核心服务
Producer:消息生产者
Consumer:消息消费者
Topic:主题,发布订阅模式下的消息统一汇集地
Queue:队列,P2P模式下的消息队列
(3)Apache Kafka
--Kafka是一种高吞吐量的分布式发布-订阅 消息系统,专为超高吞吐量的实时日志采集、实时数据同步、实时数据计算等场景来设计
	快速,单Broker每秒几百MB读取
	不停机扩集群
	消息副本冗余
	实时数据管道
--使用Scala编写

(4)Kafka Topic
Topic
	主题是已发布消息的类别名称
	发布和订阅数据必须指定主题
		主题副本数量不大于Brokers个数
Partition
	一个主题包含多个分区,默认按Key Hash分区
	每个Partition对应一个文件夹<topic_name>-<partition_id>
	每个Partition被视为一个有序的日志文件(LogSegment)
	Replication策略是基于Partition,而不是Topic
	每个Partition都有一个Leader,0或多个Followers

在这里插入图片描述

(5)Kafka数据流
--副本同步
	ISR(In-Sync Replica)
--容灾
	Leader Partition 
--高并发
--读写性能
	Consumer Group
--负载均衡	

在这里插入图片描述

(6)ZooKeeper在Kafka中的作用
--Broker注册并监控状态
	/brokers/ids
--Topic注册
	/brokers/topics
--生产者负载均衡
	每个Broker启动时,都会完成Broker注册过程,生产者会通过该节点的变化来动态地感知到Broker服务器列表的变更
--offset维护
	Kafka早期版本使用ZooKeeper为每个消费者存储offset,由于ZooKeeper写入性能较差,从0.10版本后,Kafka使用自己的内部主题维护offset

(7)Kafka的高吞吐量是如何实现的
1.顺序读写 
Kafka 的消息是不断追加到文件中的,这个特性使Kafka 可以充分利用磁盘的顺序读写性能。 顺序读写不需要硬盘磁头的寻道时间,只需很少的扇区旋转时间,所以速度远快于随机读写。
2.零拷贝 
在 Linux kernel2.2 之后出现了一种叫做"零拷贝(zero-copy)"系统调用机制,就是跳过“用户 缓冲区”的拷贝,建立一个磁盘空间和内存的直接映射,数据不再复制到“用户态缓冲区”。 
零拷贝并不是不需要拷贝,而是减少不必要的拷贝次数。通常是说在 IO 读写过程中。“零 拷贝技术”只用将磁盘文件的数据复制到页面缓存中一次,然后将数据从页面缓存直接发送 到网络中。
3.分区 
Kafka 的队列 topic 被分为了多个区 partition,每个 partition 又分为多个段 segment,所以一 个队列中的消息实际上是保存在 N 多个片段文件中通过分段的方式,每次文件操作都是对 一个小文件的操作,非常轻便,同时也增加了并行处理能力。
4.批量发送 
Kafka 允许进行批量发送消息,先将消息缓存在内存中,然后一次请求批量发送出去比如可 以指定缓存的消息达到某个量的时候就发出去,或者缓存了固定的时间后就发送出去如 100 条消息就发送,或者每 5 秒发送一次这种策略将大大减少服务端的 I/O 次数。
5.数据压缩 
Kafka 还支持对消息集合进行压缩,Producer 可以通过 GZIP 或 Snappy 格式对消息集合进行 压缩压缩的好处就是减少传输的数据量,减轻对网络传输的压力。 
6.Consumer 的负载均衡 
当一个 group 中,有 consumer 加入或者离开时,会触发 partitions 均衡.均衡的最终目的,是提升 topic 的并发消费能力。

在这里插入图片描述

(8)Kafka操作命令
开启服务:(服务开启前必须先开启zookeeper服务:zkServer.sh start)
kafka-server-start.sh /opt/soft/kafka211/config/server.properties

开启服务:(守护者模式)
kafka-server-start.sh -daemon /opt/soft/kafka211/config/server.properties

查看主题列表:
kafka-topics.sh --zookeeper zhangqi:2181 --list

查看某主题信息描述:
kafka-topics.sh --zookeeper zhangqi:2181 --describe --topic test0818

创建主题topic-demo:
kafka-topics.sh --create --zookeeper zhangqi:2181 --replication-factor 1 --partitions 1 --topic AA

开启生产者:
kafka-console-producer.sh --broker-list zhangqi:9092 --topic AA

开启消费者:
kafka-console-consumer.sh --bootstrap-server zhangqi:9092 --from-beginning --topic AA

设置可以删除主题:server-properties
delete.topic.enable=true

删除主题
kafka-topics.sh --delete --zookeeper zhangqi:2181 --topic test20200819

查看某一主题的分区的文件大小
kafka-run-class.sh kafka.tools.GetOffsetShell --topic AA --time -1 --broker-list zhangqi:9092 --partitions 0

查看某一主题的所有分区的文件大小
kafka-run-class.sh kafka.tools.GetOffsetShell --topic AA --time -1 --broker-list zhangqi:9092 

将同组的游标移到文件开头,使得同组用户可以重新读
kafka-consumer-groups.sh --bootstrap-server zhangqi:9092 --group customer --reset-offsets --all-topics --to-earliest --execute
(9)Java API
生产者(producer)
package cn.kgc.homework;

import org.apache.kafka.clients.producer.KafkaProducer;
import org.apache.kafka.clients.producer.ProducerConfig;
import org.apache.kafka.clients.producer.ProducerRecord;

import java.util.Properties;

public class ProducerLian05 {
    public static void main(String[] args) {
        //创建配置
        Properties prop = new Properties();
        
        //指定kafka服务器的地址
        prop.put(ProducerConfig.BOOTSTRAP_SERVERS_CONFIG,"zhangqi:9092");
//        acks			确保生产者可靠性设置		默认-1
//        acks=0:		不等待成功返回
//        acks=1:		等Leader写成功返回
//        acks=all:	    等Leader和所有ISR中的Follower写成功返回,all也可以用-1代替
        prop.put(ProducerConfig.ACKS_CONFIG,"all");
        //指定序列化,因为kafka接收的数据默认是键值对,如果不给键,则自动为Null
        prop.put(ProducerConfig.KEY_SERIALIZER_CLASS_CONFIG,"org.apache.kafka.common.serialization.StringSerializer");
        prop.put(ProducerConfig.VALUE_SERIALIZER_CLASS_CONFIG,"org.apache.kafka.common.serialization.StringSerializer");

        //创建一个kafka producer
        KafkaProducer<String,String> producer = new KafkaProducer<>(prop);

//        通过producer向topic发送数据
//        Integer.toString(i)和"value"+i是因为producer的泛型所致<String,String>
        for (int i = 0; i <100 ; i++) {
            producer.send(new ProducerRecord<String,String>("test04",Integer.toString(i),"value"+i));
        }
        producer.close();
    }
}

消费者(consumer)
package cn.kgc.homework;

import org.apache.kafka.clients.consumer.ConsumerConfig;
import org.apache.kafka.clients.consumer.ConsumerRecord;
import org.apache.kafka.clients.consumer.ConsumerRecords;
import org.apache.kafka.clients.consumer.KafkaConsumer;
import org.apache.kafka.common.TopicPartition;

import java.text.MessageFormat;
import java.util.Arrays;
import java.util.Properties;

public class ConsumerLian05 {
    public static void main(String[] args) {
        //创建配置
        Properties prop = new Properties();
        
        //kafka服务器配置
        prop.put(ConsumerConfig.BOOTSTRAP_SERVERS_CONFIG,"zhangqi:9092");
        //设置消费者的组
        prop.put(ConsumerConfig.GROUP_ID_CONFIG,"test");
        //反序列化,键值对
        prop.put(ConsumerConfig.KEY_DESERIALIZER_CLASS_CONFIG,"org.apache.kafka.common.serialization.StringDeserializer");
        prop.put(ConsumerConfig.VALUE_DESERIALIZER_CLASS_CONFIG,"org.apache.kafka.common.serialization.StringDeserializer");
        //offset自动提交给zookeeper进行管理
        prop.put(ConsumerConfig.ENABLE_AUTO_COMMIT_CONFIG,"true");
        //自动提交offset的时间间隔:毫秒
        prop.put(ConsumerConfig.AUTO_COMMIT_INTERVAL_MS_CONFIG,"5000");

        //创建consumer对象
        KafkaConsumer<String,String> consumer = new KafkaConsumer<String, String>(prop);

//        第一种消费方式:subscirbe消费者只能指定主题
//        consumer.subscribe(Arrays.asList("test04"));

//        第二种消费方式:assign消费者既能指定主题,还能指定分区号
        TopicPartition partition = new TopicPartition("test04",2);
        consumer.assign(Arrays.asList(partition));

        while(true){
            //消费者用poll的方式去kafka拉取数据
            ConsumerRecords<String, String> records = consumer.poll(1000);
            for (ConsumerRecord<String, String> record : records) {
                String message = MessageFormat.format("partition:{0},key:{1},value:{2}",record.partition(),record.key(),record.value());
                System.out.println(message);
            }
        }
    }
}

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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值