最近在看消息系统方面的东西。做为一个实践主义者,在看消息系统的各类实现时,不妨先粗略思考一下如何设计一个消息系统。我总觉出来有这么几个点(比较粗陋,之后继续补充):算法
队列的存储和管理缓存
用什么方式存储消息决定了这个消息系统的最终表现。网络
push仍是pullui
producer没啥好说的,确定是push,这里主要说consumer,pull的好处是能够根据consumer消费能力来处理消息,而push的好处则是实时性atom
服务横向扩展.net
是否存在单点?如何进行横向扩展的?failover如何作?翻译
保证一次消费设计
消息不丢失;不会重复消费。日志
topic模式code
是否支持单条message多个comsumer同时消费?用什么机制保证其工做?
监控
有没有监控手段?
好了,如今先来看Kafka。Kafka是LinkedIn的一个消息系统。主要用来处理日志并进行实时分析。 Kafka有一篇翻译好的文章http://www.oschina.net/translate/kafka-design。
Kafka要解决的是大吞吐量下的消息队列问题。
一些与结构无关的notes:
Java实用sendfile FileChannel.transferTo
flush与分页缓存的关系
实际中这么作意味着,数据被传输到OS内核的页面缓存中了,OS随后会将这些数据刷新到磁盘的。 这段话的思路能够考虑一下。
问题4的科学称呼:消息传递语义(Message delivery semantics)
系统能够提供的几种可能的消息传递保障以下所示:
- 最多一次—这种用于处理前段文字所述的第一种状况。消息在发出后当即标示为已使用,所以消息不会被发出去两次,但这在许多故障中都会致使消息丢失。
- 至少一次—这种用于处理前文所述的第二种状况,系统保证每条消息至少会发送一次,但在有故障的状况下可能会致使重复发送。
- 仅仅一次—这种是人们实际想要的,每条消息只会并且仅会发送一次。
这个问题已获得普遍的研究,属于“事务提交”问题的一个变种。提供仅仅一次语义的算法已经有了,两阶段或者三阶段提交法以及Paxos算法的一些变种就是其中的一些例子,但它们都有与生俱来的的缺陷。这些算法每每须要多个网络往返(round trip),可能也没法很好的保证其活性(liveness)(它们可能会致使无限期停机)。FLP结果给出了这些算法的一些基本的局限。