基于Storm的复杂事件流聚合方法设计与实现外文翻译资料

 2022-10-24 22:15:55

英语原文共 10 页,剩余内容已隐藏,支付完成后下载完整资料


外文题目: Storm @twitter The proceedings of 2014 ACM SIGMOD.

2016年 4 月 15 日

推特中的storm系统

摘要:本文介绍了如何在Twitter上应用Storm。Storm是一种实时容错和分布式数据处理系统。Storm是目前在Twitter上用来按比例以及实时运算各种关键计算问题。本文介绍了Storm的体系结构和分布式扩展和容错的方法。本文还介绍了如何在Storm中执行查询(又名拓扑结构),并展示了一些基于Storm在Twitter运行的例子。我们还提出了一个实证评估表明Storm在处理机器故障的能力的结果。Storm是在Twitter积极的发展,我们也提出了一些未来的工作方向。

1.简介

许多现代化的数据处理环境需要处理实时流数据的复杂计算。这是尤其是在推特上,每一个用户的互动要求做出一些复杂的决策,往往基于刚刚创建的数据。Storm是一种实时分布的流数据处理引擎,在Twitter 上执行实时流数据管理任务,这对于提供推特服务是至关重要的。风暴的目的是:

  1. 可伸缩性:操作团队需要容易地从Storm集群在不破坏现有数据流的情况下通过Storm拓扑结构添加或删除节点(又名。站立查询)。
  2. 弹性:容错能力对于Storm是至关重要的,因为它往往是部署在大集群,硬件组件可能失败。风暴集群必须以最小的性能影响继续处理现有的拓扑结构。
  3. 可扩展性:Storm的拓扑结构可以任意调用外部函数(例如查找mysql服务社会图),因此需要一个框架,允许可扩展性。
  4. 高效:由于风暴在实时应用中使用,它必须有良好的性能特点。Storm使用了大量的技术,包括保存所有的存储和计算数据结构在内存中。
  5. 易管理:由于Storm是在Twitter上用户交互的核心,如果有(故障或性能)与Storm相关的问题,最终用户立即会注意到。操作团队需要早期预警工具,必须能够很快地指出问题的根源。因此,易于使用的管理工具是不是一个“好的有功能”,但一个关键部分的要求。

2.storm简介

Strom运行在分布式集群上,在Twitter系统中经常运行在另外一个抽象Mesos上。客户提交拓扑到一个主节点,叫做Nimbus。Nimbus负责分配协调拓扑的执行,真正的执行由worker完成,每个worker运行一个或多个worker进程,任意时间一个单独的机器可能有不止一个worker进程,但是每个worker进程只能映射到一个拓扑结构,在同一个机器上多个worker进程可以执行相同拓扑的不同部分。Storm的高级结构在图2中显示。

每个工作进程运行一个Java虚拟机,它运行一个或多个executors。executors是由一个或多个任务组成。一个spout或bolt的实际工作是在task中完成。这样,task提供内部螺栓/内喷并行,executors提供内部拓扑结构的并行性。Worker进程作为容器为主机上运行storm拓扑提供服务。请注意,每个spout或者bolt是由一组运行在跨集群上的executors的tasks组成。数据是随机地从生产者spout或bolt向消费者bolt流动(生产者和消费者都可能有多个任务)。这种洗牌就像在并行数据库中的交换运算符。

每个worker节点上运行一个Supervisor来与Nimbus进行联系。集群的状态保存在Zookeeper中,Nimbus负责拓扑在worker节点上的调度,同时监管元组在拓扑中处理的进度。最多关于Nimbus的具体内容在2.2.1节有详细介绍。粗略地讲,一个拓扑可以被认为是从数据库系统的一个逻辑查询计划。作为拓扑的一部分,程序员强调必须产生多少关于每个spout和bolt的实例。Storm创造这些实例同时也创造这些数据流之间的联系。举个例子,推特切词拓扑的物理执行在图3中描述。我们注意到,目前程序员必须指定每一个spout和bolt的具体实例数量。未来工作的一部分是基于一些更高级别的目标,如目标性能目的,来自动拾取和动态修改这个数字。

3.Storm内部结构

3.1 Nimbus and Zookeeper

Nimbus担任类似Hadoop中中的JobTracker,它是介于用户和Storm系统之间的衔接点。Nimbus是一种Apache Thrift服务并且Storm拓扑定义是一些Thrift对象。为了提交一个job到storm集群(例如Nimbus),用户描述拓扑为一个Thrift对象然后发送这个对象到Nimbus。基于这个设计,任何编程语言都可以被用于创建storm拓扑。

作为提交拓扑的一部分,用户也上传用户代码的JAR文件到Nimbus。Nimbus结合使用本地磁盘和Zookeeper来存储状态的拓扑结构。目前的用户代码存储在Nimbus机器的本地磁盘上,而拓扑对象存储在Zookeeper中。Supervisors用一个周期性的心跳协议来与Nimbus联系,来表明拓扑是当前正在运行的或者存在多少多余空间可以来运行更多的拓扑。Nimbus跟踪需要任务的拓扑结构,然后对拓扑和Supervisors之间进行匹配。

所有的基于Nimbus和Supervisors之间的协调都在Zookeeper中进行。进一步说,Nimbus和Supervisors守护进程都是快速失败并且无状态的,所有关于它们的状态都被保存在Zookeeper中或者本地磁盘中。这一设计是storm弹性的关键,如果Nimbus服务失败,然后workers依然可以继续进行工作。并且,Supervisors在workers失败时会重启它们。然而,如果Nimbus服务失败了,用户不能提交新的拓扑。同时,如果在运行中处理拓扑的机器失败了,它们只能等到Nimbus重启之后才能被重新分配到不同的机器继续处理。未来一个有趣的研究方向就是消除这些限制让storm更加具有弹性并且更加智能地处理失败。

3.2 Supervisor

Supervisor运行在么个storm节点上,它接受来自Nimbus的任务然后将其分配给workers去执行。它同时也监管workers的健康并且在必要时产生workers。一个直观的supervisor的结构在图4中描述。正如图所示,supervisor产生三种线程。主线程读取storm的配置信息,初始化supervisor的全局映射,在文件系统中创建一个永久的局部状态,调度随时间重复的事件

同步监管事件,每10秒在事件管理线程中执行一次,这个线程负责管理已经存在的任务的变化。如果新的拓扑存在变化,它会下载必须的JAR文件和链接库,并且立即执行同步处理事件

同步处理事件,每3秒在处理事件管理线程中运行一次。这个线程负责管理那些在同一个节点上运行一个拓扑的碎片作为supervisor 的work进程。它从局部状态读取worker的心跳,将其分为有效、时间戳出界、未开始、不允许这几个状态。一个“time out”的worker表示这个worker在特殊的时间帧里未提供心疼,现在已经死亡了。一个“not started”的worker 表明这个worker属于一个新提交的拓扑还未开始运行,或者一个已经存在的拓扑其worker被移动到一个新提交的拓扑中。最后,一个“disallowed”的worker表明这个worker不能运行因为它的拓扑已经被杀死,或者这个拓扑的worker已经被移动到其他节点。

3.3 Workers and Executors

记得每个worker进程在一个JVM里运行几个executor,这些executors是在worker进程里的线程。每个executor能够运行多个任务。一个任务是一个spout或bolt的实例。一个任务严格地绑定到一个executor,因为任务是静态的。未来一个有趣的研究方向就是允许动态的任务分配来对一些更高的性能要求例如负载平衡或者满足SLO条件做出优化。元组传出和传入的流动,每个worker进程有两个专用的线程-工作接收线程和工作发送线程。工作接收线程监听TCP/IP的端口,对所有传入的元组进行去复用的操作。它检查输入元组的目标任务标识符,并且相应地将元组输入到对应其executor的队列中去。

每个executor由两个名为用户逻辑线程和执行发送线程组成。用户逻辑线程从队列中提取元组,检查其目标任务标识符,然后运行针对元组的真正任务(一个spout或bolt实例),形成输出元组。这些输出元组然后被放入对应其executor的输出队列中。然后执行发送线程从输出队列中提取这些元组,将其放入全局传送队列。全局传送队列包含来自多个executors的输出元组。

工作发送线程检查来自全局传送队列中的所有元组,基于其目标任务标识符,将其发送到下一个工作下流。对于在同一个worker上针对不同任务的输出元组,执行发送线程直接将这些元组写入目标任务中的队列。在worker内部的消息流动在图5中得到描述。

3.4 Processing Semantics

Storm一个关键的特征就是其在数据处理时提供保证。它提供两种类型的语义保证-“至少一次”和“至多一次”语义。至少一次语义保证每个元组输入到拓扑中会处理至少一次。对于至多一次语义,每个元组至多被处理一次或者由于失败被移除了。为了提供至少一次语义,拓扑扩张了一种acker bolt机制,跟踪在有向无环图中从spout发出的每个元组。举个例子,推特切词计数拓扑在图6中得到描述。

Storm给每个在系统中流动的新元组随机附属一个64比特的消息ID。这个ID是在spout第一次将这个元组从某些输入源得到时给其附属的。新的元组在一个元组被处理后就会产生,例如一个包含一条完整推特的元组通过一个bolt处理后被分割成一组热门话题,对于输入元组没一个话题产生一个元组。这些新的元组随机分配一个64比特位的消息ID,一个出处树结构让每个元组可以追溯到其祖先,当元组离开拓扑时,利用回溯机制可以知道对输出元组贡献的任务,最终到达开始处理元组的spout,在这里可以使元组移除。

一个对于此机制的基本实现就是追踪每个元组的祖先。这意味着对每个元组跟踪其出处,每个元组的ID必须保存到这个元组被处理完,导致内存开销非常大,尤其是对于复杂的拓扑。

为了避免这个问题,storm使用一种先进的按位与的实现方式。正如之前讨论的,当一个元组进入spout时,它被附属一个64位消息ID。当spout处理完这个元组时,它可能产生一个或多个元组,这些新产生的元组同样也会附属产生的64位消息ID,这些消息ID是已经与其父元组进行异或操作并且将原始元组的消息ID发送到acker bolt进行异或操作,同时发生一个时间参数。这样,acker bolt就能够追踪所以的元组。当一个元组完全被处理或者acked,它的消息ID以及其原始消息ID都发送到了acker bolt,acker bolt定位原始元组和其异或checksum。这个异或的checksum再次与元组ID进行异或操作。当这个异或的checksum最终变成0时,acker bolt将最后的ack发送到spout,spout知道这个元组已经被完成处理了。

可能由于失败,一些异或的checksum永远不会变成0.为了处理这种情况,spout于是就分配了上面提到了一个时间参数。Acker bolt跟踪这个时间过期参数,如果元组校验和如果在超时参数过期之前不能归零,元组处理失败。

剩余内容已隐藏,支付完成后下载完整资料


资料编号:[152292],资料为PDF文档或Word文档,PDF文档可免费转换为Word

原文和译文剩余内容已隐藏,您需要先支付 30元 才能查看原文和译文全部内容!立即支付

以上是毕业论文外文翻译,课题毕业论文、任务书、文献综述、开题报告、程序设计、图纸设计等资料可联系客服协助查找。