-
Notifications
You must be signed in to change notification settings - Fork 0
NSQ golang MQ 1
本文建立在通过解读NSQ源码来提升golang的编写能力。
对于阅读某个项目的源码,本人通常按以下流程开展:
- 充分理解项目的使用场景和功能;
- 对比其在同类项目中的优缺点;
- 大体构思实现该项目需要什么模块;
- 阅读源码。
当然过程不是一成不变的,对项目的理解起初往往是从外界获取,在阅读源码的过程中会有一些自己的理解融汇进去;同时源码也不是一遍就可以看明白的,这个过程需要反复折回。
在本文中,分析对象是以golang为主编程语言而开发的Message Queue:NSQ,通过上面提到的过程来进行剖析。网上已有不少NSQ的说明及代码解释文档,我会对其进行参考,也会将参考源地址做好引用。
关于MQ的解释google就可以找出很多,根据使用场景和经历不同,对MQ的理解不同。我之前项目中使用MQ场景比较简单,就是接收日志,并且没有用到多节点拓扑功能。简单理解一下,应该是有一个http的writer的端,一个内部的reader端。客户端将日志上传到writer之后无需等待服务器处理,直接收到一个成功反馈,服务端在空闲时读取reader端,将队列中的日志进行处理的一种生产者-消费者模型。
对我来说,MQ的主要作用是提供一个存放消息的area,降低各组件间的耦合度。
但是完整的MQ需要有多节点拓扑、内部+外部的api+http端口、实时及延迟消费机制和高通量读写稳定等功能,另外消息的有序无需等特点则需要根据使用场景而定。
NSQ官方文档中介绍NSQ的设计理念及NSQ特点。极客学院的wiki中提供了中文文档。
NSQ 是实时的分布式消息处理平台,其设计的目的是用来大规模地处理每天数以十亿计级别的消息。
NSQ 具有分布式和去中心化拓扑结构,该结构具有无单点故障、故障容错、高可用性以及能够保证消息的可靠传递的特征。
NSQ工具分为三大组件:
nsqd是一个守护进程,负责接收,排队,投递消息给客户端。它在 2 个 TCP 端口监听,一个给客户端,另一个是 HTTP API。同时,它也能在第三个端口监听 HTTPS。
nsqlookupd 是守护进程负责管理拓扑信息。客户端通过查询 nsqlookupd 来发现指定话题(topic)的生产者、 nsqd 节点广播的话题(topic)和通道(channel)信息。
有两个接口:nsqd 用来广播的TCP 接口和客户端及web监控界面的HTTP 接口。
nsqadmin 是一套 WEB UI,用来汇集并监控显示集群的实时统计,对topic执行部分管理任务。
nsq的周边工具,对nsq的流量管理、安全和功能的一些补充管理。
官方工具包括:nsq_stat、nsq_tail、nsq_to_file、nsq_to_http、nsq_to_nsq和to_nsq等。
topic,话题,是一个独特的数据流,通道(channel) 是消费者订阅了某个话题的逻辑分组。
单个 nsqd 可以有很多的话题,每个话题可以有多通道。一个通道接收到一个话题中所有消息的副本,启用组播方式的传输,使消息同时在每个通道的所有订阅用户间分发,从而实现负载均衡。
NSQ中的SPOF指的是消息从生产者中接收到交付给消费者的这个流程中,任何一个单一环节出现故障。
NSQ设计理念是分布式和去中心化的拓扑结构,保证信息将至少交付一次。根本原理是:
- 客户(消息接收体)表示他们已经准备好接收消息;
- NSQ 发送一条消息,并暂时将数据存储在本地做备份;
- 客户端回复 FIN(结束)或 REQ(重新排队)分别指示成功或失败。如果客户端没有回复, NSQ 会在设定的时间超时,自动重新排队该消息。
即交付消息的三种结果中,不会出现消息无缘丢失的事件。而丢失消息的情况只能是nsqd端出现问题(如非正常结束,且消息并未备份至磁盘)。因此,针对这个问题,增加nsqd的节点可以做一定程度的预防。
关于某个功能模块的特性,在模块分析部分再做详细剖析。