美文网首页
Go-Nsq资料整理和学习笔记

Go-Nsq资料整理和学习笔记

作者: 沉寂之舟 | 来源:发表于2020-01-05 10:20 被阅读0次

    写在前面:

    NSQ版本 : v1.2.0
    在源码层面,完整阅读了一个GO-Lang实际的项目-NSQ,目标是让自己从学习、熟悉Go语法,进阶到深入理解GO,理解实现工程中GO的使用和组织。现把这大半个月阅读的文章和学习笔记做一些整理。

    一. NSQ官网(nsq.io)

    这个没啥好说的,官方文档是最权威的.逐页看就是,后来发现一个中文的:

    中文文档-0.3.5

    其他介绍参考文档
    https://www.jianshu.com/p/c47e0350bb2e
    https://www.cnblogs.com/li-peng/category/1537661.html
    https://segmentfault.com/a/1190000012362544
    http://blog.rayxxzhang.com/index.html
    http://luodw.cc/2017/04/14/nsqd/
    https://www.cnblogs.com/li-peng/p/11435083.html


    二. NSQ依赖

    NSQ已经改成go modules来管理包.

    
    module github.com/nsqio/nsq
    
    require (
        github.com/BurntSushi/toml v0.3.1
        github.com/bitly/go-hostpool v0.0.0-20171023180738-a3a6125de932
        github.com/bitly/timer_metrics v0.0.0-20170606164300-b1c65ca7ae62
        github.com/blang/semver v3.5.1+incompatible
        github.com/bmizerany/perks v0.0.0-20141205001514-d9a9656a3a4b
        github.com/davecgh/go-spew v1.1.1 // indirect
        github.com/golang/snappy v0.0.0-20180518054509-2e65f85255db
        github.com/judwhite/go-svc v1.0.0
        github.com/julienschmidt/httprouter v1.2.0
        github.com/mreiferson/go-options v0.0.0-20190302015348-0c63f026bcd6
        github.com/nsqio/go-diskqueue v0.0.0-20180306152900-74cfbc9de839
        github.com/nsqio/go-nsq v1.0.7
        github.com/pmezard/go-difflib v1.0.0 // indirect
        github.com/stretchr/testify v1.2.2 // indirect
        golang.org/x/sys v0.0.0-20181221143128-b4a75ba826a6 // indirect
    )
    
    

    可以看出基本大部分都是自己的依赖(其中nsqio和bilty部分),都是一些小的工具包.
    唯一需要注意的是httprouter,nsq用它来装饰处理http请求.

    package 简要说明
    go-difflib python迁移的对比包
    go-diskqueue 官方提供的文件记录包-用于在channel满的时候,作为backendQueue保存到文件中
    go-hostpool 把主机信息池化
    go-nsq NSQ官方提供的客户端实现
    go-options 读取命令行配置工具
    go-spew 格式化打印
    go-svc 用于包装为系统服务(会识别环境)
    http-router 轻量级http请求路由
    perks 产生图标的工具包
    semver 解析版本字符串的工具(如1.0.3-beta)
    snappy 压缩算法包
    x/sys GO官方扩展包
    timer_metrics 计时测量
    toml nsq使用toml文件格式作为配置持久化

    三. Go-nsq (V1.0.7)

    • 首先要理解go-nsq作为官方提供的客户端,怎么使用,先堆一堆参考文档:

    https://nicksors.cc/2018/08/15/%E6%B6%88%E6%81%AF%E9%98%9F%E5%88%97%E4%B9%8B%E3%80%8A02-NSQ%E5%AE%9E%E8%B7%B5%E7%AF%87%E3%80%8B.html
    https://cloud.tencent.com/developer/article/1070860
    https://segmentfault.com/a/1190000009194607
    https://lihaoquan.me/2016/6/20/using-nsq.html
    https://juejin.im/post/5d3e3a44f265da1bae39439a
    https://www.cnblogs.com/li-peng/p/11435083.html

    • 其次是看源码,代码不多.我理解核心还是搞懂Conn,Delegate,Consumer,Producer之间的关系.默认的Consumer和Producer都实现了ConnDelegate接口,用来把连接conn上的事件传导给具体的
      Consumer和Producer去完成.

    Delegate使得它们之间的关系解耦,避免了Conn和Consumer双向引用.

    • 测试代码:
      1. Config_test.go | Go语言可以很方便用数组形式构造测试案例
      2. Producer_test.go | 测试生产者
      3. Consumer_test.go | 测试消费者

    四. nsq-internal

    nsq-internal是几个实现共用的一些工具包

    package 简要说明
    app 包含FloatArray和StringArray,用在解析命令参数
    auth Authorization结构,用在权限控制(本次阅读忽略)
    clusterinfo 用来外呼http请求,获取信息
    dirlock 锁定目录(windows无效)
    httpapi 带截止时间的http请求封装(主要和go-nsq中的不同)
    lg 日志工具
    pqueue 以Item为元素的优先级队列,其中Item.value是个空接口,用在diskBackend中.奇怪的是InflightQueue是用Message实现的一套.
    protocol 用来表明自己能处理的tcp协议报文.(nsqd和nsqlookupd都有自己的实现)
    quanltile 统计用的火焰图数据
    statsd 登记统计信息的服务器调用简单包装
    stringy nsq用的几个字符串函数工具包
    test nsq对测试的工具包,其中FakeNetConn可以伪装为一个连接
    util WaitGroupWrapper把普通的函数(无参数,无返回值)同步调用包装成异步调用
    version 表明版本号(目前1.2.1)
    writers BoundaryBufferedWriter和SpreadWriter两种实现

    五. nsq-apps

    由nsq提供的可执行程序的源码,除了nsqd、nsqlookup、nsqadmin这几个服务端封装外,基本都是用go-nsq(客户端)实现特定功能的命令行工具。

    package 简要说明
    nsq_stat 使用http_api实现对特定的topic,channel的监控(打印控制台)
    nsq_tail 订阅消费特定Topic消息,实现对特定的channel监控(打印控制台)
    nsq_to_file 订阅消费特Channel消息,记录到文件
    nsq_to_http 把Nsq消息通过http发出
    nsq_to_nsq 桥接Nsq消息-转发
    to_nsq 读取文件中message,发送到nsqd中

    六. nsq-nsqd

    NSQD是整个消息中间件的核心,所幸很多人都分析了,这里不需要再累述,看代码的同时,结合牛人的文章即可:

    NSQ源码分析之概述(不错)
    http://luodw.cc/2016/12/08/nsq01/
    http://luodw.cc/2016/12/13/nsqlookupd/
    http://luodw.cc/2017/04/14/nsqd/
    nsq源码分析
    https://www.cnblogs.com/hlxs/p/11445103.html
    nsq源码学习
    https://segmentfault.com/a/1190000012362544
    NSQ源码剖析之nsqd(不错)
    http://shanks.leanote.com/post/NSQ%E6%BA%90%E7%A0%81%E5%89%96%E6%9E%90%E4%B9%8BNSQD
    nsq源码阅读(nsqd)(不错)
    http://sksun.com.cn/2018/06/13/nsq%E6%BA%90%E7%A0%81%E9%98%85%E8%AF%BB-nsqd/
    http://sksun.com.cn/2018/06/12/nsq%E6%BA%90%E7%A0%81%E9%98%85%E8%AF%BB-nsqlookupd/

    • 结构:
      NSQ结构是多层次的,NSQD有个topicMap,记录所有的Topic;topic有个channelMap,记录所有的Channel,Channel有个clients,记录所有的消费者.这些结构都有一个ctx指针,指向NSQD自身.

    • 启动:
      先启动TcpServer,HttpServer,处理报文
      再启动queueScanLoop(动态调整queueScanWorker的数目,处理in-flight和deffered queue的消息),lookupLoop(和nsqlookupd服务器连接),statsdLoop(和stasd服务器连接)

    • 消息处理:
      略,上面文章讲太多了..

    • 代码阅读中一些疑问:

    1. Topic创建时机?
      在Publish时,如果不存在,会自动创建.

    2. Channel创建时机?
      在Sub是,如果不存在,会自动创建.

    3. deferredMessages与inFlightMessages
      Channel内部维护2个队列,infight表示正在和client交互(等到client返回FIN才删除,保证消息至少被接收一次),deferred表示可以提前给nsqd发送message,等到时间到才合法.

    4. BackendQueue与ephemeral
      如果声明为ephemera,则如果消息超过infight队列长度,就会被丢弃.而BackendQueue可以用go-diskqueue包提供的方法保存到文件中.

    5. 消息有序性?
      NSQ不保证,可能无序(requeue机制,多节点机制)

    6. 丢消息?
      如果异常退出,infightMsg可能会丢

    7. RDY意义:
      RDY是订阅方告知NSQD服务器自身处理能力的方法,这样避免服务器快速给客户端发消息,客户端处理不过来的情况(Rx中背压)


    七. nsq-nsqlookupd

    与nsqd类似,nsqlookupd通过TCP和Http两种方式向外提供服务.

    1. RegistrationDB
      登记nsq信息的内存DB,使用registrationMap,ProducerMap两层MAP,并且实现了add,remove,find,这些操作,便于上层进行调用.
    2. lookup_protocol_v1
      提供tcp服务,只有Ping,Identify,Register,Unregister四个方法,也就是说,只有nsqd才会使用tcp和nsqlookupd连接通讯.(Category有topic和channel,client三种)
    3. http
      提供http服务,消费者使用nsqlookupd提供的方法感知,而producer是需要直连nsqd的.
      提供了"/topic/create","/topic/delete"这种,不是给nsqd用的,是给go-nsq客户端或者nqadmin手工删除topic用的.

    八. nsq-nsqadmin

    admin相对比较简单(go部分),通过notify构造AdminAction向外主动POST,或者通过http向外提供服务.而且,它本身并不存储任何数据,需要时,都是使用httpServer中的client向nslookupd或者nsqd查询(类似于gateway).这里用了internal/clusterinfo,先调用nslookupd,不行就直接请求nsqd(需要遍历所有的nsqd,为了效率,还是搭建nslookupd吧).
    前端页面部分用了backdone+jquery+gulp.未看...

    九. 其他

    1. bench目录: 用python写的批量测试用例
    2. 有赞nsq (https://github.com/youzan/nsq)
      发现有赞Fork了一个分支,并做了改进,有机会再细看一下...

    How we redesign the NSQ-Smart Client

    How we redesigned the NSQ - NSQ重塑之详细设计
    视频观看

    How we redesigned the NSQ - 其他特性及未来计划

    有赞NSQ多集群多机房设计

    相关文章

      网友评论

          本文标题:Go-Nsq资料整理和学习笔记

          本文链接:https://www.haomeiwen.com/subject/bhuqactx.html