Push VS Pull

An initial question we considered is whether consumers should pull data from brokers or brokers should push data to the consumer. In this respect Kafka follows a more traditional design, shared by most messaging systems, where data is pushed to the broker from the producer and pulled from the broker by the consumer.

Kafka遵循传统设计,也是被大多数消息系统所采用的,即,producer push数据到broker,consumer从broker那里pull数据。

A push-based system has difficulty dealing with diverse consumers as the broker controls the rate at which data is transferred. The goal is generally for the consumer to be able to consume at the maximum possible rate; unfortunately, in a push system this means the consumer tends to be overwhelmed when its rate of consumption falls below the rate of production.

基于push的系统在面对不同的消费者的时候需要控制数据传输的速率这是很困难的,一般消费者都是以最大速率去消费的,不幸的是这对于push系统来说意味着当消费的速率低于生产的速率时消费者有崩溃的倾向。而基于pull的系统就有很好的属性,消费者可以简单的落后,并且在可能的时候迎头赶上。在消费者感觉快要崩溃的时候可以缓和一下,获取传输速率完全靠消费者机灵。

基于pull的系统的另一个优势在于broker可以将自己的数据批量的发送给消费者。而基于push的系统必须选择是立即发送请求还是累积更多的数据再发请求,而且发送以后它不知道消费者是否能很快的处理它。基于pull的系统就能够很好的解决这个问题,因为消费者总是拉取在当前日志的位置之后的所有可用的消息。

基于pull的系统有一个缺陷就是如果broker没有数据,消费者会一直循环等待,有效的繁忙的等待直到有数据到达。为了避免这个问题, 我们可以让消费者在请求的时候以“长轮询”的形式阻塞,直到有数据到达。

Consumer Position

大部分的消息系统在broker中维护关于消息是否已经被消费的元数据。因此,一个消息被分发给消费者以后broker可以理解处理或者等到消费者确认。

或许你还没有意识到让broker和consumer就消息是否已经被消息达成一致是一个很重要的问题。如果每次消息被分发出去以后broker就立即将这条消息标记为consumed,这个时候如果消费者处理消息失败了(可能是因为它宕机了或者请求超时了或者其它的原因),那么这条消息就丢失了。为了解决这个问题,许多消息系统增加一个确认特性,这就意味着在消息被发送以后只能将它们标记为sent而不是consumed,broker会等待来自消费者的确认,之后才会将这条消息标记为consumed。这个策略虽然解决了丢失消息的问题,但是又带来了新的问题。首先,如果消费者已经处理完消息,但是在它发送确认之前它失败了,那么这种情况下会导致消息被消费两次。第二个问题跟性能有关,现在broker对于每条消息必须维护多个状态(首先锁定它以至于它不会被分发第二次,然后永久的标记它为consumed以至于它肯能会被删除)。棘手的问题必须被处理,比如消息发送后没有确认。

Kafka handles this differently. Our topic is divided into a set of totally ordered partitions, each of which is consumed by exactly one consumer within each subscribing consumer group at any given time. This means that the position of a consumer in each partition is just a single integer, the offset of the next message to consume. This makes the state about what has been consumed very small, just one number for each partition. This state can be periodically checkpointed. This makes the equivalent of message acknowledgements very cheap.

Kafka对这些问题的处理不同,主题被划分为一系列有序的分区,在任意时刻,一个分区只能被订阅这个主题的每个消费者组中的一个消费者消费。这就意味着,消费者的位置在每个分区中仅仅是一个整数,这个整数就是即将要消费的下一个消息的offset(偏移量)。这使得标记关于消息是否已经被消费的状态变得很简单,每个分区仅仅一个数。这个状态可以周期性的被检查。这跟消息确认是等价的,而且也是非常廉价的。

消费者可以故意倒回到一个旧的offset去重新消费数据。当然,这一点违反了队列的公共契约,但事实上这是许多消费者的一个基本特性。例如,如果消费者的代码有bug,并且在一些消息被消费以后才发现,那么消费者可以重新消费这些消息以修复这个bug。

参考 http://kafka.apache.org/documentation/#design

Kafka Consumer的更多相关文章

  1. 【原创】Kafka Consumer多线程实例

    Kafka 0.9版本开始推出了Java版本的consumer,优化了coordinator的设计以及摆脱了对zookeeper的依赖.社区最近也在探讨正式用这套consumer API替换Scala ...

  2. Kafka设计解析(四)- Kafka Consumer设计解析

    本文转发自Jason’s Blog,原文链接 http://www.jasongj.com/2015/08/09/KafkaColumn4 摘要 本文主要介绍了Kafka High Level Con ...

  3. 【原创】kafka consumer源代码分析

    顾名思义,就是kafka的consumer api包. 一.ConsumerConfig.scala Kafka consumer的配置类,除了一些默认值常量及验证参数的方法之外,就是consumer ...

  4. Understanding Kafka Consumer Groups and Consumer Lag

    In this post, we will dive into the consumer side of this application ecosystem, which means looking ...

  5. Kafka consumer处理大消息数据问题

    案例分析 处理kafka consumer的程序的时候,发现如下错误: ERROR [2016-07-22 07:16:02,466] com.flow.kafka.consumer.main.Kaf ...

  6. 【原创】Kafka Consumer多线程实例续篇

    在上一篇<Kafka Consumer多线程实例>中我们讨论了KafkaConsumer多线程的两种写法:多KafkaConsumer多线程以及单KafkaConsumer多线程.在第二种 ...

  7. 读Kafka Consumer源码

    最近一直在关注阿里的一个开源项目:OpenMessaging OpenMessaging, which includes the establishment of industry guideline ...

  8. kafka consumer 配置详解

    1.Consumer Group 与 topic 订阅 每个Consumer 进程都会划归到一个逻辑的Consumer Group中,逻辑的订阅者是Consumer Group.所以一条message ...

  9. kafka consumer 0.8.2.1示例代码

    package test_kafka; import java.util.ArrayList; import java.util.HashMap; import java.util.List; imp ...

  10. Kafka consumer group位移0ffset重设

    本文阐述如何使用Kafka自带的kafka-consumer-groups.sh脚本随意设置消费者组(consumer group)的位移.需要特别强调的是, 这是0.11.0.0版本提供的新功能且只 ...

随机推荐

  1. 类A是公共的,应在名为A.java的文件中声明错误

    第一种!!! “类A是公共的,应在名为A.java的文件中声明”这句话需要分两步来理解: 1.如果类A被声明为公共的(public),那么必须将类A保存在名为A.java的文件中: 2.反之,在一个文 ...

  2. Gym100814B Gym100814F Gym100814I(异或) ACM International Collegiate Programming Contest, Egyptian Collegiate Programming Contest (2015) Arab Academy for Science and Technology

    今日份的训练题解,今天写出来的题没有昨天多,可能是因为有些事吧... Gym100814B 这个题就是老师改卷子,忘带标准答案了,但是他改了一部分卷子,并且确定自己改的卷子没出错,他想从改过的卷子里把 ...

  3. android企业级商城源码、360°全景图VR源码、全民直播源码等

    Android精选源码 [新版]Android技术博客精华汇总 开源了:乐乐音乐5.0-Android音乐播放器 android实现仿真水波纹效果源码 360°全景图VR,这是一个值得把玩的APP a ...

  4. [国嵌笔记][019][Eclipse集成开发环境]

    Eclipse集成开发环境的作用 可以编译程序,也可以对程序进行在线调试 集成开发环境 1.JLink连接开发板的JTAG 2.JLink连接PC的USB 3.eclipse软件 4.gdb serv ...

  5. keepalived VS zookeeper

    转载请标明出处http://www.cnblogs.com/haozhengfei/p/e3db73cb83afb213a3bff43a850d56c4.html keepalived VS zook ...

  6. 根据PV统计出前三的热门板块,并统计出热门板块下的用户数--方式一

    根据PV统计出前三的热门板块,并统计出热门板块下的用户数--方式一 测试数据 java代码 package com.hzf.spark.study; import java.util.ArrayLis ...

  7. Java 反射和内省实现spring的IOC和DI

    1.构造两个JavaBean package com.spring.model; public class People { private Car car; public Car getCar() ...

  8. 量化投资与Python之pandas

    pandas:数据分析 pandas是一个强大的Python数据分析的工具包.pandas是基于NumPy构建的. pandas的主要功能具备对其功能的数据结构DataFrame.Series集成时间 ...

  9. Windows10下用Anaconda3安装TensorFlow教程

    这是我在自己的笔记本电脑上用Anaconda3安装TensorFlow的教程 1. 安装好Anaconda3版本 (1) 注:可以发现最新版本是Anaconda5了(没关系,下载就是了) (2) 注意 ...

  10. DS18B20温度传感器知识点总结

    2018-01-1818:20:48 感觉自己最近有点凌乱,一个很简单的问题都能困扰自己很久.以前能很好使用和调试的DS18B20温度传感器,今天愣是搞了很久,妈卖批. 仅仅一个上拉电阻就困扰了我很久 ...