46

Kafka -- 处理请求 | 点滴积累

 4 years ago
source link: http://zhongmingmao.me/2019/09/15/kafka-process-request/?
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
  1. Kafka自定义了一组请求协议,用于实现各种各样的交互操作
    • PRODUCE请求用于生产消息,FETCH请求用于消费消息,METADATA请求用于请求Kafka集群元数据信息
  2. Kafka 2.3总共定义了45种请求格式,所有请求都通过TCP网络以Socket的方式进行通讯

处理请求方案

实现简单,但吞吐量太差,只适用于请求发送非常不频繁的场景

1
2
3
4
while (true) {
Request request = accept(connection);
handle(request);
}

单独线程处理

为每个请求都创建一个新的线程异步处理,完全异步,但开销极大,只适用于请求发送频率很低的场景

1
2
3
4
5
while (true) {
Request request = accept(connection);
Thread thread = new Thread(() -> { handle(request); });
thread.start();
}

Reactor模式

kafka-process-request-reactor.png
  1. Reactor模式是事件驱动架构的一种实现方式,特别适合应用于处理多个客户端并发向服务器端发起请求的场景
  2. 多个客户端会发送请求给Reactor,Reactor有个请求分发线程Acceptor,将不同的请求下发到多个工作线程中处理
  3. Acceptor线程只用于请求分发,不涉及具体的逻辑处理,非常轻量级,有很高的吞吐量
    • 工作线程可以根据实际业务处理需要任意增减,从而动态调节系统负载能力

Kafka

kafka-process-request-reactor-kafka.png
  1. Broker端有一个SocketServer组件,类似于Reactor模式中的Dispatcher
    • 也有对应的Acceptor线程和一个工作线程池(即网络线程池,参数设置num.network.threads,默认值为3
  2. Acceptor线程采用轮询的方式将入站请求公平地发到所有网络线程中
    • 实现简单,避免了请求处理的倾斜,有利于实现较为公平的请求处理调度

kafka-process-request-reactor-kafka-io-pool.png
  1. 网络线程拿到请求后,并不是自己处理,而是将请求放入到一个共享请求队列
  2. Broker端还有一个IO线程池,负责从共享请求队列中取出请求,执行真正的处理
    • 如果是PRODUCE请求,将消息写入到底层的磁盘日志
    • 如果是FETCH请求,则从磁盘页缓存中读取消息
  3. IO线程池中的线程才是执行请求逻辑的线程,参数num.io.threads,默认值为8
  4. IO线程处理完请求后,会将生成的响应发送到网络线程池的响应队列
    • 然后由对应的网络线程负责将Response返回给客户端
  5. 请求队列是所有网络线程共享的,而响应队列是每个网络线程专属
    • Purgatory组件用于缓存延时请求
    • acks=allPRODUCE请求,必须等待ISR中所有副本都接收消息后才能返回
      • 此时处理该请求的IO线程必须等待其他Broker的写入结果,当请求不能处理时,就会暂存在Purgatory中
      • 等到条件满足后,IO线程会继续处理该请求,并将Response放入对应网络线程的响应队列中
  6. Kafka将PRODUCE、FETCH这类请求称为数据类请求,把LeaderAndIsr、StopReplica这类请求称为控制类请求
    • Kafka 2.3,正式实现了数据类请求控制类请求分离完全拷贝一套组件,实现两类请求的分离)

About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK