JStorm 源码解析:ACK 机制

Ack 机制是 storm 能够保证消息至少被处理一次(at least once)的核心,从而保证消息不丢失。在 topology 有向无环图中,spout 向 bolt 发射消息,上游 bolt 也会向下游 bolt 发射消息,storm 设置了一类 acker 类型的系统 bolt 用于接收所有组件发送的 ack 消息,监控数据在 topology 中的处理情况。如果处理成功则发送 __acker_ack 消息给 spout,否则发送 __acker_fail 消息给 spout,然后 spout 依据相应的消息类型采取一定的应对措施(例如消息重发等)。 Ack 算法利用了数学上的异或操作来实现对整个 tuple tree 的运行状况的判断。在一个由一条消息构成的 tuple t...

阅读全文

JStorm 源码解析:worker 的启动和运行机制

上一篇我们分析了 supervisor 节点的启动和运行过程,提及到 supervisor 的核心工作就是基于 ZK 从 nimbus 节点领取分配给它的任务,并启动 worker 执行。一个 worker 就是一个 JVM 进程,运行在 supervisor 节点上,多个 task 可以同时运行在一个 worker 进程之中,每个 task 都对应一个线程。 Worker 进程的启动位于 Worker 类中,前面我们在分析 supervisor 节点的启动过程时提及到了对于 Worker 类 main 函数的触发,supervisor 在启动相应 worker 进程时会指定 topologyId、supervisorId、workerPort、workerId,以及 classpat...

阅读全文

JStorm 源码解析:supervisor 的启动和运行机制

Supervisor 节点可以理解为单机任务调度器,它负责监听 nimbus 节点的任务资源分配,启动相应的 worker 进程执行 nimbus 分配给当前节点的任务,同时监测 worker 的运行状态,一旦发现有 worker 运行异常,就会杀死该 worker 进程,并将原先分配给 worker 的任务交还给 nimbus 节点进行重新分配。 Supervisor 节点的启动过程位于 Supervisor 类中,main 方法的实现比较简单,主要就是创建了一个 Supervisor 类对象,并调用实例方法 Supervisor#run,该方法的实现如下: 1234567891011121314151617181920212223242526272829303132333435pu...

阅读全文

JStorm 源码解析:nimbus 的启动和运行机制

本篇我们一起分析一下 nimbus 节点的启动和运行机制。Nimbus 节点是 storm 集群的调度者和管理者,它是集群与用户交互的窗口,负责 topology 任务的分配、启动和运行,也管理着集群中所有的 supervisor 节点的运行,监控着整个集群的运行状态,并将集群运行信息汇集给 UI 进行展示。 Nimbus 节点的启动过程位于 NimbusServer 类中,这是一个驱动类,main 方法中会加载集群配置文件,包括 default.yaml 和 storm.yaml,并将配置文件内容与启动时的命令行参数一起封装成 map 对象便于后续使用,真正的启动逻辑位于 NimbusServer#launchServer 方法中: 1234567891011121314151617...

阅读全文

JStorm 源码解析:基础线程模型

在具体开始分析 storm 集群的启动和运行机制之前,我们先来看一下基础的线程模型,在整个 storm 的实现中有很多地方用到它,所以将其单独拎出来先分析说明一下,后面看到相应的类就大致知道其内在的运行过程啦。 在 storm 的实现中,有很多实现了 RunnableCallback 类的子类,这些类实例化之后都被传递给了 AsyncLoopThread 对象,示例如下: 12345678910111213141516171819public class MyRunnableCallback extends RunnableCallback { private static AtomicInteger count = new AtomicInteger(); @O...

阅读全文

JStorm 源码解析:拓扑任务的资源分配过程

上一篇我们分析了 topology 构建和提交过程在客户端的逻辑,并最终通过 submitTopology 方法向 storm 集群的 nimbus 节点提交任务。Nimbus 以 Thrift RPC 服务的方式运行,相应 thrift 接口方法实现位于 ServiceHandler 类中,下面我们从 ServiceHandler#submitTopology 方法切入,分析 nimbus 节点之于客户端提交任务的资源分配过程,该方法包装了 ServiceHandler#submitTopologyWithOpts 方法。 Storm 集群的任务提交主要分为三种类型:新任务提交、热部署,以及灰度发布。ServiceHandler#submitTopologyWithOpts 方法统一...

阅读全文

JStorm 源码解析:拓扑的构建和提交过程

我们按照 storm 规范开发的 spout 和 bolt 需要使用 TopologyBuilder 构建成有向无环图(拓扑),并指定消息的分组方式,然后提交给 storm 集群执行,本篇我们将分析 topology 的构建和提交过程。前面分析 storm 的编程接口时曾介绍过 StormTopology 这个 thrift 类,topology 在构建完成之后会封装成一个 StormTopology 对象,并通过 RPC 方法提交给 storm 集群的 nimbus 节点。 一. 拓扑的构建过程拓扑结构在 storm 集群中以 StormTopology 对象的形式表示,这是一个 thrift 类,其定义如下: 12345struct StormTopology { 1:...

阅读全文

JStorm 源码解析:编程接口

Storm topology 是由 spout 和 bolt 构建的有向无环图,其中 spout 是图的起始节点,用于发送数据,而 bolt 是图的中间节点和末端节点,用于对数据进行处理。下面我们先用一个简单的 wordcount 示例来回忆一下 storm 的基本使用,然后对示例中涉及到的 storm 编程接口从源码层面分析其内在实现。 一. 简单示例:Word Count本节中我们将实现一个 wordcount 程序,其中 spout 用于发送句子,bolt 负责对句子进行切分、单词统计,以及最终打印等工作。 实现 Spout实现一个 spout 最常见的方式是继承 BaseRichSpout 抽象类,我们的句子发送 spout 实现如下: 12345678910111213141...

阅读全文

JStorm 源码解析:整体架构

Storm 是一个基于 ZK 协调的分布式任务实时调度系统,属于流式(实时)计算引擎的一类。在目前的大数据和人工智能背景下流式计算是公司大部分业务的刚性需求,能够实现在百十毫秒内完成对用户行为的计算并执行具体的策略,例如依据用户的行为对其实施风控等。 当下市面上已有很多流式计算引擎产品,但是 storm 的出现基本上统一了这一领域,不过近几年也出现了一些新的产品可以撼动 storm 的地位,比如 flink、spark streaming 等。不可否认的是,现阶段还是有很多公司的业务运行在 storm 集群上,这样一个毫秒级延迟的分布式实时计算引擎还是有很多地方值得我们一起去探寻其设计与实现原理。 JStorm 架构设计JStorm 是在 storm 的基础上基于 java 语言重写而...

阅读全文

那些年,面试被虐过的红黑树

面试官:小桂子是吧,看你简历上写着精通 java 编程,想必对 java 已经掌握的很好了吧? 小桂子:系呀系呀,一直都用 java 写 bug 呢~ 面试官:那你说说 jdk1.7 之前 HashMap 的底层实现原理呗,另外为什么在高并发场景下可能造成较高的 CPU 占用? 小桂子:这个。。。好像是红黑树? 面试官:哦?你说的是 jdk1.8 之后的设计,既然你提到了,那就聊聊红黑树这个数据结构吧,这里是白纸和笔,手写一棵吧! 小桂子:哎呀,哎呀哎呀,老师,突然肚子好疼,我要去一下厕所,一会儿就回来~~~ 面试处处是套路呀。。。不知道你是否有和小桂子一样尴尬的面试经历呢,如果有的话欢迎到评论区留言,说出你的故事~ 接下来我们进入正题,开始探究面试官为难小桂子的红黑树。说到红黑...

阅读全文

Powered by hexo & Theme by hiero   Copyright © 2015-2018 浙ICP备 16010916  号,指 · 间 All Rights Reserved.