Storm-源码分析-acker (backtype.storm.daemon.acker)
backtype.storm.daemon.acker
设计的巧妙在于, 不用分别记录和track, stream过程中所有的tuple, 而只需要track root tuple, 而所有中间过程都通过异或更新track entry
acker-init, 在spout发送一个tuple时触发, 初始化这个root tuple的track entry
acker-ack, 在blot ack一个tuple的时候触发, 会对该tuple的anchors-to-ids中记录的每个(root, edge)进行ack, 并出于优化还会附带登记新的edge(对acker透明, 在发送前已经完成)
acker-fail, 任一个过程中的tuple fail, 都会导致这个root tuple失败
(defn mk-acker-bolt []
(let [output-collector (MutableObject.)
pending (MutableObject.)]
(reify IBolt
(^void prepare [this ^Map storm-conf ^TopologyContext context ^OutputCollector collector]
(.setObject output-collector collector)
(.setObject pending (RotatingMap. 2)) ;;用RotatingMap来缓存每个tuple的track信息
)
(^void execute [this ^Tuple tuple]
(let [^RotatingMap pending (.getObject pending)
stream-id (.getSourceStreamId tuple)] ;;从ack tuple中取出streamid
(if (= stream-id Constants/SYSTEM_TICK_STREAM_ID) ;;收到system_tick_stream, rotate pending, spout的pending和acker的pending超期时间是一样的, 都取决于system-tick
(.rotate pending)
(let [id (.getValue tuple 0) ;;else,其他的stream,取出tuple id
^OutputCollector output-collector (.getObject output-collector)
curr (.get pending id) ;;取出相应tuple的track entry
curr (condp = stream-id
ACKER-INIT-STREAM-ID (-> curr ;;初始化tuple的track entry
(update-ack (.getValue tuple 1)) ;;更新entry中的track value
(assoc :spout-task (.getValue tuple 2))) ;;记录该tuple和spout-task的关系, 这样在ack或fail的时候才知道通知谁
ACKER-ACK-STREAM-ID (update-ack curr (.getValue tuple 1));;ack, 用val和原来的entry value做异或
ACKER-FAIL-STREAM-ID (assoc curr :failed true))] ;;fail, 直接把entry的:failed设true
(.put pending id curr)
(when (and curr (:spout-task curr))
(cond (= 0 (:val curr)) ;;val为0, 表示该tuple的所有edge都被成功ack
(do
(.remove pending id) ;;从pending中删除track entry, 并向相应的spout-task发送ack消息
(acker-emit-direct output-collector
(:spout-task curr)
ACKER-ACK-STREAM-ID
[id]
))
(:failed curr) ;;:failed为true, 表示该tuple失败
(do
(.remove pending id) ;;从pending中删除track entry, 并向相应的spout-task发送fail消息
(acker-emit-direct output-collector
(:spout-task curr)
ACKER-FAIL-STREAM-ID
[id]
))
))
(.ack output-collector tuple) ;;acker bolt也是bolt, 所以最后完成对该ack tuple的ack
))))
(^void cleanup [this]
)
)))
(defn- update-ack [curr-entry val]
(let [old (get curr-entry :val 0)] ;;取出entry中的value值,默认设为0
(assoc curr-entry :val (bit-xor old val)) ;;将old和新val异或, 赋给entry的value
))
Storm-源码分析-acker (backtype.storm.daemon.acker)的更多相关文章
- Storm源码分析--Nimbus-data
nimbus-datastorm-core/backtype/storm/nimbus.clj (defn nimbus-data [conf inimbus] (let [forced-schedu ...
- JStorm与Storm源码分析(四)--均衡调度器,EvenScheduler
EvenScheduler同DefaultScheduler一样,同样实现了IScheduler接口, 由下面代码可以看出: (ns backtype.storm.scheduler.EvenSche ...
- JStorm与Storm源码分析(三)--Scheduler,调度器
Scheduler作为Storm的调度器,负责为Topology分配可用资源. Storm提供了IScheduler接口,用户可以通过实现该接口来自定义Scheduler. 其定义如下: public ...
- JStorm与Storm源码分析(二)--任务分配,assignment
mk-assignments主要功能就是产生Executor与节点+端口的对应关系,将Executor分配到某个节点的某个端口上,以及进行相应的调度处理.代码注释如下: ;;参数nimbus为nimb ...
- JStorm与Storm源码分析(一)--nimbus-data
Nimbus里定义了一些共享数据结构,比如nimbus-data. nimbus-data结构里定义了很多公用的数据,请看下面代码: (defn nimbus-data [conf inimbus] ...
- storm源码分析之任务分配--task assignment
在"storm源码分析之topology提交过程"一文最后,submitTopologyWithOpts函数调用了mk-assignments函数.该函数的主要功能就是进行topo ...
- storm源码分析之topology提交过程
storm集群上运行的是一个个topology,一个topology是spouts和bolts组成的图.当我们开发完topology程序后将其打成jar包,然后在shell中执行storm jar x ...
- Nimbus<三>Storm源码分析--Nimbus启动过程
Nimbus server, 首先从启动命令开始, 同样是使用storm命令"storm nimbus”来启动看下源码, 此处和上面client不同, jvmtype="-serv ...
- JStorm与Storm源码分析(五)--SpoutOutputCollector与代理模式
本文主要是解析SpoutOutputCollector源码,顺便分析该类中所涉及的设计模式–代理模式. 首先介绍一下Spout输出收集器接口–ISpoutOutputCollector,该接口主要声明 ...
- Storm-源码分析-EventManager (backtype.storm.event)
Protocol and DataType 大体结构, 定义protocol EventManager, 其实就是定义interface 函数event-manager, 主要做2件事 1. 启动ev ...
随机推荐
- 反射学习1、反射机制的介绍和基本的API的使用
关于动态语言: 一般而言,开发者社群说到动态语言,大致认同的一个定义是:“程序运行时,允许改变程序结构或变量类型,这种语言称为动态语言”.从这个观点看,Perl,Python,Ruby是动态语言,C+ ...
- datatables 相关文章
http://blog.csdn.net/zhu_xiao_yuan/article/details/51252300 datatables参数配置详解 http://blog.csdn.net/j ...
- php服务器端与android客户端通信问题
http://www.oschina.net/question/616446_90760
- IOS中的多线程和NSRunLoop概述(转载)
线程概述 有些程序是一条直线,从起点到终点,如Hello World,运行打印完,它的生命周期便结束了:有些程序是一个圆,不断循环,直到将它切断,如操作系统,一直运行直到你关机. 一个运行着的程序就 ...
- 微信小程序,时间戳转为日期格式
//数据转化 function formatNumber(n) { n = n.toString() ] ? n : ' + n } /** * 时间戳转化为年 月 日 时 分 秒 * number: ...
- Web安全测试(一)-手工安全测试方法&修改建议
常见问题 1.XSS(CrossSite Script)跨站脚本攻击 XSS(CrossSite Script)跨站脚本攻击.它指的是恶意攻击者往Web 页面里插入恶意 html代码,当用户浏览该页之 ...
- 使用jmeter实现对jar包的调用
一.前言 在我们测试接口的过程中,可能有时需要用到第三方jar包来生成一些测试数据(如有时需要对参数的输入值使用第三方jar包进行加密操作),涉及到这种的情况,普遍做法是:手动调用jar包获得需要的值 ...
- Ajax.BeginForm提示不支持live属性或方法的错误
解决: 在nuget下载最新版本的jquery.unobtrusive-ajax.min.js文件 Ajax异步请求: 引用JS: <script type="text/javascr ...
- Oracle 10gR2 RAC 启动与关闭
一. 检查共享设备 一般情况下, 存放OCR 和 Voting Disk 的OCFS2 或者raw 都是自动启动的. 如果他们没有启动,RAC 肯定是启动不了的. 1.1 如果使用ocfs2的,检查o ...
- 0、手把手教React Native实战之开山篇
##作者简介 东方耀 Android开发 RN技术 facebook github android ios 原生开发 react reactjs nodejs 前端 ...