分布式消息系统研究报告之Kafka

最近在看消息系统方面的东西。做为一个实践主义者,在看消息系统的各类实现时,不妨先粗略思考一下如何设计一个消息系统。我总觉出来有这么几个点(比较粗陋,之后继续补充):算法

  1. 队列的存储和管理缓存

    用什么方式存储消息决定了这个消息系统的最终表现。网络

  2. push仍是pullui

    producer没啥好说的,确定是push,这里主要说consumer,pull的好处是能够根据consumer消费能力来处理消息,而push的好处则是实时性atom

  3. 服务横向扩展.net

    是否存在单点?如何进行横向扩展的?failover如何作?翻译

  4. 保证一次消费设计

    消息不丢失;不会重复消费。日志

  5. topic模式code

    是否支持单条message多个comsumer同时消费?用什么机制保证其工做?

  6. 监控

    有没有监控手段?

好了,如今先来看Kafka。Kafka是LinkedIn的一个消息系统。主要用来处理日志并进行实时分析。 Kafka有一篇翻译好的文章http://www.oschina.net/translate/kafka-design

Kafka要解决的是大吞吐量下的消息队列问题。

  1. 队列过长时,不少消息系统都不给力 Kafka使用文件系统来进行存储,基本没有什么限制。文件都是马上flush。
  2. 将消息打包成MessageSet,自己是Buffer的思想,例如nagle算法
  3. 消息压缩 支持GZIP
  4. 将消息强制排序,并用“最高水位标记”(high water mark)"来记录消费者状态
  5. 用groupId+atomicInteger代替guid来标识每一条消息,减小复杂性

一些与结构无关的notes:

  1. Java实用sendfile FileChannel.transferTo

  2. flush与分页缓存的关系

实际中这么作意味着,数据被传输到OS内核的页面缓存中了,OS随后会将这些数据刷新到磁盘的。 这段话的思路能够考虑一下。

  1. 问题4的科学称呼:消息传递语义(Message delivery semantics)

    系统能够提供的几种可能的消息传递保障以下所示:

    1. 最多一次—这种用于处理前段文字所述的第一种状况。消息在发出后当即标示为已使用,所以消息不会被发出去两次,但这在许多故障中都会致使消息丢失。
    1. 至少一次—这种用于处理前文所述的第二种状况,系统保证每条消息至少会发送一次,但在有故障的状况下可能会致使重复发送。
    1. 仅仅一次—这种是人们实际想要的,每条消息只会并且仅会发送一次。

    这个问题已获得普遍的研究,属于“事务提交”问题的一个变种。提供仅仅一次语义的算法已经有了,两阶段或者三阶段提交法以及Paxos算法的一些变种就是其中的一些例子,但它们都有与生俱来的的缺陷。这些算法每每须要多个网络往返(round trip),可能也没法很好的保证其活性(liveness)(它们可能会致使无限期停机)。FLP结果给出了这些算法的一些基本的局限。

相关文章
相关标签/搜索