031. Kafka 入门及使用

1. 简介


  • Kafka 是 LinkedIn 使用 Scala 编写具有高水平扩展和高吞吐量的分布式消息系统。
  • Kafka 对消息保存时根据 Topic 进行归类,发送消息者称为 producer,消息接收者称为 consumer,此外 Kafka 集群有多个 Kafka 实例组成,每个实例(server)称为 broker。
  • 无论是 Kafka 集群,还是 producer 和 consumer 都依赖于 zookeeper 来保证系统可用性,为集群保存一些 meta 信息。

2. 主流 MQ 对比


  • 数据吞吐量:Kafka > RabbitMQ > ActiveMQ
  • 数据准确性:RabbitMQ > ActiveMQ > Kafka

ActiveMQ

RabbitMQ

Kafka

所属社区/公司

Apache

Mozilla Public License

Apache/LinkedIn

开发语言

Java

Erlang

Scala

支持的协议

OpenWire、STOMP、REST、XMPP、AMQP

AMQP

仿 AMQP

事务

支持

不支持

0.11 开始支持

集群

支持(不擅长)

支持(不擅长)

支持

负载均衡

支持

支持

支持

动态扩容

不支持

不支持

支持(zk)

3. Kafka 主要特性


  • Kafka 是一个流处理平台,流平台需如下特性:
    • 可发布和订阅流数据,类似于消息队列或者企业级消息系统。
    • 以存储容错的方式存储流数据。
    • 可以在流数据产生时就进行处理。
  • Kafka 适合什么样的场景?
    • 基于 Kafka,构造实时流数据管道,让系统或应用之间可靠地获取数据。
    • 构建实时流式应用程序,处理流数据或基于数据做出反应。

4. 相关概念


  • AMQP(Advanced Message Queuing Protocal),是一个提供统一消息服务的标准高级消息队列协议,是应用层协议的一个开放标准,为面向消息的中间件而设计。
image-20200706181759845

概念

描述

server

AMQP 服务端,接受客户端连接,实现 AMQP 消息队列和路由功能的进程。

producer

生产者,向 broker 发布消息的客户端应用程序。

consumer

消费者,向消息队列请求消息的客户端应用程序。

Topic

是数据主题,是 Kafka 用来代表一个数据流的一个抽象。发布数据时,可用 topic 对数据进行分类,也作为订阅数据时的主题。一个 Topic 同时可有多个 producer、consumer。

Partition

每个 Partition 是一个顺序的、不可变的 record 序列,partition 中的 record 会被分配一个自增长的 id,我们称之为 offset。

Replication

每个 partition 还会被复制到其他服务器作为 replication,这是一种冗余备份策略。

Record

每条记录都有 key、value、timestamp 三个信息

image-20200706181957892
image-20200706182113029

5. Kafka 核心 API


四个核心 API

API

描述

Producer API

允许一个应用程序发布一串流式的数据到一个或者多个 Kafka topic。

Consumer API

允许一个应用程序订阅一个或者多个 topic,并且对发布给它们的流式数据进行处理。

Stream API

允许一个应用程序作为一个流处理器,消费一个或者多个 topic 产生的输入流,然后生产一个输出流到一个或者多个 topic 中去,在输入输出中进行有效的转换。

Connector API

允许构建并运行可重用的生产者或者消费者,将 Kafka topics 连接到已存在的应用程序或者数据系统。比如,连接到一个关系型数据库,捕捉表(table)的所有变更内容。

Kafka API - producer
image-20200706182325026
代码语言:javascript
复制
Properties props = new Properties();
props.put("batch.size", 16384); // 默认值为 16384
props.put("linger.ms", 16384); // 默认值为 0
props.put("acks", "all");
props.put("retries", 1);
// ...

Producer<String, String> producer = new KafkaProducer(props);
ProducerRecord<String, String> record = new ProducerRecord<>("my-topic", "key", "value");
producer.send(record);

producer.close();

  • producer 会为每个 partition 维护一个缓冲,用来记录还没有发送的数据,每个缓冲区大小用 batch.size 指定,默认值为 16K。
  • linger.ms:buffer 中的数据在达到 batch.size 前,需要等待的时间。
  • acks:用来配置请求成功的标准。
    • 0:不检查返回。
    • 1:leader partition 请求成功即可。
    • all:leader partition 及 follower partition 请求成功才行。

6. Kafka 使用场景


1. 消息系统
  • 消息系统被用于各种场景,如解耦数据生产者,缓存未处理的消息。Kafka 可作为传统的消息系统的替代者,与传统消息系统相比,Kafka 有更好的吞吐量、更好的可用性,这有利于处理大规模的消息。

  • 根据经验,通常消息传递对吞吐量要求较低,但可能要求较低的端到端延迟,并经常依赖 Kafka 可靠的 durable 机制。
  • 在这方面,Kafka 可以与传统的消息传递系统(ActiveMQ 和 RabbitMQ)相媲美。
2. 存储系统
  • 写入到 Kafka 的数据是落地到了磁盘上,并且有冗余备份,Kafka 允许 producer 等待确认,通过配置,可实现直到所有的 replication 完成复制才算写入成功,这样可保证数据的可用性。
  • Kafka 认真对待存储,并允许 client 自行控制读取位置,你可以认为 Kafka 是一种特殊的文件系统,它能够提供高性能、低延迟、高可用的日志提交存储。
3. 日志聚合(Kafka 官方提出,装得有点大)
  • 日志系统一般需要如下功能:日志的收集、清洗、聚合、存储、展示。
  • Kafka 常用来替代其他日志聚合解决方案。
  • 和 Scribe、Flume 相比,Kafka 提供同样好的性能、更健壮的堆积保障、更低的端到端延迟。
  • 日志会落地,导致 Kafka 做日志聚合更昂贵。
  • Kafka 可实现日志的清洗(需要编码)、聚合(可靠但昂贵)、存储。
  • ELK 是现在比较流行的日志系统。在 Kafka 的配合下才是更成熟的方案,Kafka 在 ELK 技术栈中,主要起到 buffer 的作用,必要时可进行日志的汇流。
4. 跟踪网站活动
  • Kafka 的最初是作用就是,将用户行为跟踪管道重构为一组实时发布-订阅源。把网站活动(浏览网页、搜索或其他的用户操作)发布到中心 topics 中,每种活动类型对应一个 topic。基于这些订阅源,能够实现一系列用例,如实时处理、实时监视、批量地将 Kafka 的数据加载到 Hadoop 或离线数据仓库系统,进行离线数据处理并生成报告。
  • 每个用户浏览网页时都生成了许多活动信息,因此跟踪活动的数据量通常非常大。(Kafka 实际应用)
5. 流处理
  • Kafka 社区认为仅仅提供数据生产、消息机制是不够的,他们还要提供流数据实时处理机制,从 0.10.0.0 开始,Kafka 通过提供 Stream API 来提供轻量、但功能强大的流处理。实际上就是 Stream API 帮助解决流引用中一些棘手的问题,比如:处理无序的数据,代码变化后再次处理数据,进行有状态的流式计算。
  • Stream API 的流处理包含多个阶段,从 input topics 消费数据,做各种处理,将结果写入到目标 topic,Stream API 基于 Kafka 提供的核心原语构建,它使用 Kafka consumer、producer 来输入、输出,用 Kafka 来做状态存储。
  • 流处理框架:flink、spark streaming、Storm、Samza 才是正统的流处理框架,Kafka 在流处理中更多的是扮演流存储的角色。