kafka笔记

Kafka是一种分布式的、基于发布/订阅的消息系统

特点:

消息持久化:通过O(1)的磁盘数据结构提供数据的持久化
高吞吐量:每秒百万级的消息读写
分布式:扩展能力强
多客户端支持:java、php、python、c++ ……
实时性:生产者生产的message立即被消费者可见

基本组件

Broker:每一台机器叫一个Broker
Producer:日志消息生产者,用来写数据,当对接flume的时候,flume的sink就是Kafka的producer生产者
Consumer:消息的消费者,用来读数据,可以通过spark streaming作为消费者来读取数据
Topic:不同消费者去指定的Topic中读,不同的生产者往不同的Topic中写
Partition:新版本才支持Partition,在Topic基础上做了进一步区分分层

一个生产者的数据可以分配给多个partition,并且这多个partition可以对接到多个groupid里面,但是每个groupid必须消费一个完整的生产者所分配的分区数据,即如下图所示:
这两个
这两个p1表示同一个生产者的不同分区的数据,它们的结果必须到一个完整的groupid里面。
当consumer的个数大于分区的个数时,会出现有的消费者无法消费的情况,如图所示:
在这里插入图片描述
• Kafka内部是分布式的、一个Kafka集群通常包括多个Broker
• zookeeper负载均衡:将Topic分成多个分区,每个Broker存储一个或多个Partition
• 多个Producer和Consumer同时生产和消费消息

在这里插入图片描述
在这里插入图片描述
一个生产者->两个分区->一个消费者:
在上述这种情况下,生产者的数据分别到两个分区当中,然后合并返回一个消费者里面,那么它们的顺序可能会与生产者输入的顺序不同。
在这里插入图片描述

#查看某个topic主题详情,例如分区数
bin/kafka-topics.sh --describe --zookeeper localhost:2181 --topic test

• 一个Topic是一个用于发布消息的分类或feed名,kafka集群使用分区的日志,每个分区都是有顺序且不变的消息序列。
• commit的log可以不断追加。消息在每个分区中都分配了一个叫offset的id序列来唯一识别分区中的消息
每一个分区的日志是用topic-分区id为名称的文件夹,例如test-0 test-1表示topic为test的两个分区
• 无论发布的消息是否被消费,kafka都会持久化一定时间(可配置)。
• 在每个消费者都持久化这个offset在日志中。通常消费者读消息时会使offset值线性的增长,但实际上其位置是由消费者控制,它可以按任意顺序来消费消息。比如复位到老的offset来重新处理。
message(消息)是通信的基本单位,每个producer可以向一个topic(主题)发布一些消息。如果consumer订阅了这个主题,那么新发布的消息就会广播给这些consumer。
生产者可以发布数据到它指定的topic中,并可以指定在topic里哪些消息分配到哪些分区(比如简单的轮流分发各个分区或通过指定分区语义分配key到对应分区)。
生产者直接把消息发送给对应分区的broker,而不需要任何路由层。
批处理发送,当message积累到一定数量或等待一定时间后进行发送。可以减少网络请求次数。
• 一种更抽象的消费方式:消费组(consumer group)
1、如果所有的消费者实例都有相同的消费组,这样就像传统的queue方式。
2、如果所有的消费者实例都有不同的消费组,这样就像传统的发布订阅方式。
一个partition只能对应一个consumer,但是一个consumer可以对应多个partition(指的是同一个groupid里面的),如下图:
在这里插入图片描述
对于第一个group A来说p0、p3->C1的原因是这样的话,只需要建立一个连接就行。
• Kafka存储布局简单:Topic的每个Partition对应一个逻辑日志(一个日志为相同大小的一组分段文件)
• 每次生产者发布消息到一个分区,代理就将消息追加到最后一个段文件中。 当发布的消息数量达到设定值或者经过一定的时间后,段文件真正flush磁盘中。 写入完成后,消息公开给消费者。
• 与传统的消息系统不同,Kafka系统中存储的消息没有明确的消息Id。
• 消息通过日志中的逻辑偏移量来公开。
在这里插入图片描述
Kafka虽然也是要写入磁盘,但是它却比较快的原因是采用了zero-copy机制。
• Kafka代理是无状态的:意味着消费者必须维护已消费的状态信息offset。这些信息由消费者自己维护,代理完全不管。这种设计非常微妙,它本身包含了创新。
Kafka默认采用at least once的消息投递策略。
• 三种保证策略:
At most once 消息可能会丢,但绝不会重复传输
At least one 消息绝不会丢,但可能会重复传输
Exactly once 每条消息肯定会被传输一次且只传输一次
• 由于kafka中一个topic中的不同分区只能被消费组中的一个消费者消费,就避免了多个消费者消费相同的分区时会导致额外的开销(如要协调哪个消费者消费哪个消息,还有锁及状态的开销)。kafka中消费进程只需要在代理和同组消费者有变化时时进行一次协调(这种协调不是经常性的,故可以忽略开销)。

### 尚硅谷 Kafka 学习笔记 #### 创建 Kafka 生产者并发送消息 为了创建一个简单的 Kafka 生产者并向指定主题发送消息,在命令行工具中可以执行如下操作。通过 `bin/kafka-console-producer.sh` 脚本启动生产者客户端,并指定了引导服务器地址以及目标主题名称[^1]。 ```bash [atguigu@hadoop102 kafka]$ bin/kafka-console-producer.sh --bootstrap-server hadoop102:9092 --topic first > hello ``` 此命令允许用户手动输入要发布的消息内容,每条新消息以回车键结束提交给集群处理。 #### 修改消费者配置文件设置分组ID 对于希望自定义消费逻辑的应用程序来说,调整消费者的配置参数是非常重要的一步。具体而言,可以通过编辑 `/opt/module/kafka/config/consumer.properties` 文件内的 `group.id` 属性来设定唯一的消费者组标识符[^4]。 ```properties [atguigu@hadoop103 config]$ vi consumer.properties group.id=atguigu ``` 这里展示了如何更改默认值为特定字符串(如 "atguigu"),从而确保不同实例之间不会相互干扰。 #### 实现自定义分区器 当业务需求涉及到更复杂的路由策略时,则可能需要用到自定义的 Partitioner 类型。下面给出了一种基于关键字匹配决定消息所属分区的方法示例代码片段[^5]: ```java public class MyPartitioner implements Partitioner { @Override public int partition(String topic, Object key, byte[] keyBytes, Object value, byte[] valueBytes, Cluster cluster) { String inputValue = (value != null && !"".equals(value)) ? value.toString() : ""; if ("hello".contains(inputValue)){ return 1; } else{ return 0; } } @Override public void close(){} @Override public void configure(Map<String, ?> configs){} } ``` 这段 Java 程序实现了 `Partitioner` 接口,并覆盖了其抽象方法 `partition()` 来判断传入的消息体是否包含预设关键词 `"hello"`;如果条件成立则返回整数 `1` 表明该记录应分配至编号为 `1` 的物理分区上,反之亦然。 #### 关于日志与数据存储机制的理解 值得注意的是,Kafka 中的日志目录实际上是指向实际保存二进制编码后的消息集合的位置。由于这些对象经过序列化过程变得难以直观理解,因此建议开发者熟悉相关概念以便更好地管理和维护系统性能[^2]。 另外,关于偏移量 Offset 的管理方式也值得深入探讨。每个存储单元都会依据首次出现位置获得独一无二的名字格式——即形似 `xxxxxx.kafka` 这样的文件名模式,其中 x 可能代表任意长度但始终递增的一串数字字符[^3]。
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值