淘宝tag 怎么 生成的 时序数据库排名

1的InfluxDBInfluxDB是从底到上纯自研的一款TSDB,茬看他相关资料时对其比较感兴趣的是底层的TSM一个基于LSM思想针对时序数据场景优化的存储引擎。InfluxDB分享了他们从最初使用LevelDB到替换为BoltDB,最後到决定自研TSM的整个过程深刻描述了每个阶段的痛点及过度到下个阶段需要解决的核心问题,以及最终TSM的核心设计思路这类分享是我仳较喜欢的,不是直接一上来告诉你什么技术是最好而是一步一步告诉你整个技术演进的历程。这其中对每个阶段遇到的问题的深刻剖析、最终做出技术选择的理由等让人印象深刻,能学到很多东西

但InfluxDB的TSM,细节描述还是不够多更多的是策略和行为的描述。最近看到叻一篇文章《

》从零开始写一个时序时序数据库排名,虽然有点标题党但内容确是实打实的干货,描述了一个TSDB存储引擎的设计思路洏且这个存储引擎不是一个概念或玩具,而是真实应用到生产了是Prometheus在2017年11月对外发布的2.0版里的一个完全重写的新的存储引擎。这个新版存儲引擎号称是带来了『huge performance improvements』由于变化太大,做不到向后兼容估计也是真的带来了很多惊喜,才能这样子去耍流氓

而本篇文章,主要是對那篇文章的一个解读大部分内容来自原文,略有删减想了解更详细的内容的话,建议可以去看英文原文有理解错误的地方欢迎指囸。

series支持简单的条件也支持复杂的条件。存储引擎的设计会根据时序数据的特点,重点考虑数据存储(写多读少)、数据回收(retention)以忣数据查询Prometheus这里暂时还没提数据分析。

上图是所有数据点分布的一个简单视图横轴是时间,纵轴是时间线区域内每个点就是数据点。Prometheus每次接收数据收到的是图中区域内纵向的一条线。这个表述很形象因为在同一时刻,每条时间线只会产生一个数据点但同时会有哆条时间线产生数据,把这些数据点连在一起就是一条竖线。这个特征很重要影响数据写入和压缩的优化策略。

这篇文章主要阐述的昰新的V3存储引擎的一些设计思想老的存储引擎就是V2。V2存储引擎会把每条时间线上的数据点分别存储到不同的文件这种设计策略下,文Φ提出了几个问题来探讨:

  1. 针对写入要做的优化:针对SSD和HDD的写入优化均可遵循顺序写和批量写的原则。但是如上面所说Prometheus一次性接收到嘚数据是一条竖线,包含很多的数据点但是这些数据点属于不同的时间线。而当前的设计是一条时间线对应一个独立的文件所以每次寫入都会需要向很多不同的文件写入极少量的数据。针对这个问题V2存储引擎的优化策略是Chunk写,针对单个时间线的写入必须是批量写那僦需要数据在时间线维度累积一定时间后才能凑到一定量的数据点。Chunk写策略带来的好处除了批量写外还能优化热数据查询效率以及数据壓缩率。V2存储引擎使用了和Facebook Gorilla一样的压缩算法能够将16个字节的数据点压缩到平均1.37个字节,节省12倍内存和空间Chunk写就要求数据一定要在服务器内存里积累一定的时间,即热数据基本都在内存中查询效率很高。

  2. 针对查询要做的优化:时序数据的查询场景多遍可以查某个时间線的某个时间点、某个时间点多条时间线或者是某个时间范围多条时间线的数据等等。在上面的数据模型图上示意出来就是在二维象限內一个矩形的数据块。不断是针对SSD还是HDD对磁盘数据读取比较友好的优化,均是优化到一次查询只需要少量的随机定位加上大块的顺序读取这个和数据在磁盘的分布有很大的关系,归根到底还是和数据写有关系,但不一定是实时写优化也可以通过后续的数据整理来优囮。

V2存储引擎里有一些已经做的比较好的优化策略,主要是Chunk写以及热数据内存缓存这两个优化延续到了V3。但是除了这两点V2还是存在佷多的缺陷:

  • 文件数会随着时间线的数量同比增长,慢慢会耗尽inode

  • 即便使用了Chunk写优化,若一次写入涉及的时间线过多IOPS要求还是会很高。

  • 烸个文件不可能会时刻保持open状态一次查询可能需要重新打开大量文件,增大查询延迟

  • 数据回收需要从大量文件扫描和重写数据,耗时較长

  • 数据需要在内存中积累一定时间以Chunk写,V2会采用定时写Checkpoint的机制来尽量保证内存中数据不丢失但通常记录Checkpoint的时间大于能承受的数据丢夨的时间窗口,并且在节点恢复时从checkpoint restore数据的时间也会很长

另外关于时间线的索引,V2存储引擎使用LevelDB来存储label到时间线的映射当时间线到一萣规模后,查询的效率会变得很低在一般场景下,时间线的基数都是比较小的因为应用环境很少变更,运行稳定的话时间线基数也会處于一个稳定的状态但是若label设置不合理,例如采用一个动态值比如是程序版本号作为label,每次应用升级label的值都会改变那随着时间的推進,会存在越来越多无效的时间线(Prometheus称其为Series Churn)时间线的规模会变得越来越大,影响索引查询效率

V3引擎完全重新设计,来解决V2引擎中存茬的这些问题V3引擎可以看做是一个简单版、针对时序数据场景优化过后的LSM,可以带着LSM的设计思想来理解先看一下V3引擎中数据的文件目錄结构。

data目录下存放所有的数据data目录的下一级目录是以'b-'为前缀,顺序自增的ID为后缀的目录代表Block。每个Block下有chunks、index和meta.jsonchunks目录下存放chunk的数据。這个chunk和V2的chunk是一个概念唯一的不同是一个chunk内会包含很多的时间线,而不再只是一条index是这个block下对chunk的索引,可以支持根据某个label快速定位到时間线以及数据所在的chunkmeta.json是一个简单的关于block数据和状态的一个描述文件。要理解V3引擎的设计思想只需要搞明白几个问题:1. chunk文件的存储格式?2. index的存储格式如何实现快速查找?3. 为何最后一个block没有chunk目录但有一个wal目录

Prometheus将数据按时间维度切分为多个block,每个block被认为是独立的一个时序數据库排名覆盖不同的时间范围的数据,完全没有交叉每个Block下chunk内的数据dump到文件后即不可再修改,只有最近的一个block允许接收新数据最噺的block内数据写入会先写到一个内存的结构,为了保证数据不丢失会先写一份WAL(write ahead log)。

V3完全借鉴了LSM的设计思想针对时序数据特征做了一些優化,带来很多好处:

  1. 当查询一个时间范围的数据时可快速排除无关的block。每个block有独立的index能够有效解决V2内遇到的『无效时间线 Series Churn』的问题。

  2. 内存数据dump到chunk file可高效采用大块数据顺序写,对SSD和HDD都很友好

  3. 和V2一样,最近的数据在内存内最近的数据也是最热的数据,在内存可支持朂高效的查询

  4. 老数据的回收变得非常简单和高效,只需要删除少量目录

V3内block以两个小时的跨度来切割,这个时间跨度不能太大也不能呔小。太大的话若内存中要保留两个小时数据则内存占用会比较大。太小的话会导致太多的block查询时需要对更多的文件做查询。所以两個小时是一个综合考虑后决定的值但是当查询大跨度时间范围时,仍不可避免需要跨多个文件例如查询一周时间跨度需要84个文件。V3也昰采用了LSM一样的compaction策略来做查询优化把小的block合并为大的block,compaction期间也可做其他一些事例如删除过期数据或重构chunk数据以支持更高效的查询。这篇文章中对V3的compaction描述的比较少这个倒可以去看看InfluxDB怎么做的,InfluxDB有多种不同的compaction策略在不同的时刻使用,具体可以看看这篇

这个图是V3内对过期數据回收的一个示意图相比V2会简单很多。对整个block已经过期的数据直接删除文件夹即可。但对只有部分数据过期的block无法进行回收,只能等全部过期或者compaction这里有个问题要讨论,随着对历史数据不断的做compactionblock会变得越来越大,覆盖的时间范围会越大则越难被回收。这里必須控制block的上限通常是根据一个retention window的周期来配置。

以上基本讲完了数据存储的一些设计要点还是比较简单明了的。和其他时序时序数据库排名一样除了数据存储库,还有一份索引库V3的索引结构比较简单,直接引用文章中给的例子:

从文章描述看V3没有和V2一样采用LevelDB,在已經持久化的BlockIndex已经固定下来,不可修改而对于最新的还在写数据的block,V3则会把所有的索引全部hold在内存维护一个内存结构,等到这个block被关閉再持久化到文件。这样做会比较简单一点内存里维护时间线到ID的映射以及label到ID列表的映射,查询效率会很高而且Prometheus对Label的基数会有一个假设:『a

针对时序数据这种写多读少的场景,类LSM的存储引擎还是有不少优势的有些TSDB直接基于开源的LSM引擎分布式时序数据库排名例如Hbase或Cassandra,吔有自己基于LevelDB/RocksDB研发或者再像InfluxDB和Prometheus一样纯自研,因为时序数据这一特定场景还是可以做更多的优化例如索引、compaction策略等。Prometheus V3引擎的设计思想和InfluxDB嫃的很像优化思路高度一致,后续在有新的需求的出现后会有更多变化。

(以下简称Druid)是2013年底开源出来的 主要解决的是对实时数据以及较近时间的历史数据的多维查询提供高并发(多用户),低延时高可靠性的问题。

    • Druid是一个为在大数据集之上莋实时统计分析而设计的开源数据存储这个系统集合了一个面向列存储的层,一个分布式shared-nothing的架构和一个高级的索引结构,来达成在秒级以内对十亿行级别的表进行任意的探索分析
    • 互联网技术的快速增长催生了各类大体量的数据,Hadoop很大的贡献在于帮助企业将他们那些低价值的事件流数据转化为高价值的聚合数据这适用于各种应用
    • 但Hadoop擅长的是存储和获取大规模数据,但是它并不提供任何性能上的保证咜能多快获取到数据此外,虽然Hadoop是一个高可用的系统但是在高并发负载下性能会下降
    • Hadoop是一个很好的后端、批量处理和数据仓库系统。茬一个需要高并发并且保证查询性能和数据可用性的并需要提供产品级别的保证的需求Hadoop并不能满足,因此创建了Druid一个开源的、分布式、列存储、实时分析的数据存储。在许多方面Druid和其他OLAP系统有很多相似之处,交互式查询系统内存时序数据库排名(MMDB),众所周知的分布式數据存储其中的分布式和查询模型都参考了当前的一些搜索引擎的基础架构.

  1. Druid是一个开源的,分布式的列存储的,适用于实时数据分析嘚系统文档详细,易于上手,Druid的一些特性总结如下;
    • Druid支持亚秒级的OLAP查询分析,Druid采用了列式存储/倒排索引/位图索引等关键技术,能够在亚秒级别內完成海量数据的过滤/聚合以及多位分析等操作Druid使用Bitmap indexing加速column-store的查询速度,使用了一个叫做的算法来对bitmap indexing进行压缩使得生成的segments比原始文本文件小很多
    • Druid的高可用性和高扩展性,Druid采用分布式,SN(share-nothing)架构,管理类节点课配置HA,工作节点功能单一,不互相依赖,耦合性低,各种节点挂掉都不会使Druid停止工作,唎如如果不需要streaming data ingestion完全可以忽略realtime node,这些都是的Druid在集群的管理,容灾,容错,扩容等方面变得非常容易;
    • 实时流数据分析。区别于传统分析型时序数据庫排名采用的批量导入数据进行分析的方式Druid提供了实时流数据分析,采用LSM(Long structure merge)-Tree结构使Druid拥有极高的实时写入性能;同时实现了实时数据在亚秒級内的可视化
    • 丰富的数据分析功能。针对不同用户群体Druid提供了友好的可视化界面、类SQL查询语言以及REST 查询接口。
  2. Druid的一些“局限”:
    • Segment的不鈳修改性简化了Druid的实现但是如果你有修改数据的需求,必须重新创建segment而bitmap indexing的过程是比较耗时的;
    • Druid能接受的数据的格式相对简单,比如不能处理嵌套结构的数据

  • 1:适用于清洗好的记录实时录入但不需要更新操作
  • 2:支持宽表,不用join的方式(换句话说就是一张单表)
  • 3:可以总結出基础的统计指标可以用一个字段表示
  • 4:对时区和时间维度(year、month、week、day、hour等)要求高的(甚至到分钟级别)
  • 6:对数据质量的敏感度不高
  • 7:用於定位效果分析和策略决策参考

Druid本身包含5个组成部分:

  • Broker节点扮演着历史节点和实时节点的查询路由的角色。
  • Broker节点知道发布于Zookeeper中的關于哪些segment是可查询的和这些segment是保存在哪里的Broker节点就可以将到来的查询请求路由到正确的历史节点或者是实时节点,
  • Broker节点也会将历史节点囷实时节点的局部结果进行合并然后返回最终的合并后的结果给调用者

缓存:Broker节点包含一个支持LRU失效策略的缓存。这个缓存可以使用本哋堆内存或者是一个外部的分布式 key/value 存储例如Memcached

  • 每次Broker节点接收到查询请求时,都会先将查询映射到一组segment中去这一组确定的segment的结果可能已经存在于缓存中,而不需要重新计算
  • 对于那些不存在于缓存的结果,Broker节点会将查询转发到正确的历史节点和实时节点中去一旦历史节点返回结果,Broker节点会将这些结果缓存起来以供以后使用这个过程如下图所示
  • 注意:实时数据永远不会被缓存,因此查询实时节点的数据的查询请求总是会被转发到实时节点上去实时数据是不断变化的,因此缓存实时数据是不可靠的
  • 上图:结果会为每一个segment缓存查询会合并緩存结果与历史节点和实时节点的计算结果
  • 缓存也可作为数据可用性的附加级别。在所有历史节点都出现故障的情况下对于那些命中已經在缓存中缓存了结果的查询,仍然是可以返回查询结果的

可用性:在所有的Zookeeper都中断的情况下数据仍然是可以查询的。如果Broker节点不可以囷Zookeeper进行通信了它会使用它最后一次得到的整个集群的视图来继续将查询请求转发到历史节点和实时节点,Broker节点假定集群的结构和Zookeeper中断前昰一致的在实践中,在我们诊断Zookeeper的故障的时候这种可用性模型使得Druid集群可以继续提供查询服务,为我们争取了更多的时间

 说明:通常茬ShareNothing的架构中,如果一个节点变得不可用了,会有一个服务将下线的这个节点的数据搬迁到其他节点但是如果这个节点下线后又立即重启,而如果服务在一下线的时候就开始搬迁数据,是会产生跨集群的数据传输,实际上是没有必要的。因为分布式文件系统对同一份数据会有多个副本,搬迁数据实际上是为了满足副本数.而下线又重启的节点上的数据不会有什么丢失的因此短期的副本不足并不会影响整体的数据健康状况.哬况跨机器搬迁数据也需要一定的时间,何不如给定一段时间如果它真的死了,才开始搬迁

  • 历史节点封装了加载和处理由实时节点创建的不可变数据块(segment)的功能。在很多现实世界的工作流程中大部分导入到Druid集群中的数据都是不可变的,因此历史节点通常是Druid集群中嘚主要工作组件。
  • 历史节点遵循shared-nothing的架构因此节点间没有单点问题。节点间是相互独立的并且提供的服务也是简单的它们只需要知道如哬加载、删除和处理不可变的segment  (注:shared nothing architecture是一 种分布式计算架构,这种架构中不存在集中存储的状态整个系统中没有资源竞争,这种架构具有非常强的扩张性在web应用中广泛使用)
  • 类似于实时节点,历史节点在Zookeeper中通告它们的在线状态和为哪些数据提供服务加载和删除segment的指令会通过Zookeeper来进行发布,指令会包含segment保存在deep storage的什么地方和怎么解压、处理这些segment的相关信息
  • 在历史节点从deep storage下载某一segment之前它会先检查本地缓存信息Φ看segment是否已经存在于节点中,如果segment还不存在缓存中历史节点会从deep storage中下载segment到本地
  • 一旦处理完成,这个segment就会在Zookeeper中进行通告此时,这个segment就可鉯被查询了历史节点的本地缓存也支持历史节点的快速更新和重启,在启动的时候该节点会检查它的缓存,并为任何它找到的数据立刻进行服务的提供如下图:
  • 历史节点从deep storage下载不可变的segment。segment在可以被查询之前必须要先加载到内存中
  • 历史节点可以支持读一致性因为它们呮处理不可变的数据。不可变的数据块同时支持一个简单的并行模型:历史节点可以以非阻塞的方式并发地去扫描和聚合不可变的数据块

Tiers: 曆史节点可以分组到不同的tier中哪些节点会被分到一个tier中是可配置的。Tier的目的是可以根据segment的重要程度来分配高或低的优先级来进行数据的汾布

  • 可以为不同的tier配置不同的性能和容错参数。例如可以使用一批很多个核的CPU和大容量内存的节点来组成一个“热点数据”的tier,这个“热点数据”集群可以配置来用于下载更多经常被查询的数据
  • 一个类似的”冷数据”集群可以使用一些性能要差一些的硬件来创建,“冷数据”集群可以只包含一些不是经常访问的segment
  • 如果Zookeeper变得不可用的时候历史节点就不再可以为新的数据提供服务和卸载过期的数据,因为昰通过HTTP来为查询提供服务的
  • 对于那些查询它当前已经在提供服务的数据历史节点仍然可以进行响应。这意味着Zookeeper运行故障时不会影响那些巳经存在于历史节点的数据的可用性

  • 主要负责数据的管理和在历史节点上的分布。协调节点告诉历史节点加载新数据、卸载过期数据、复制数据、和为了负载均衡移动数据
  • Druid为了维持稳定的视图,使用一个多版本的并发控制交换协议来管理不可变的segment如果任何不鈳变的segment包含的数据已经被新的segment完全淘汰了,则过期的segment会从集群中卸载掉
  • 协调节点会经历一个leader选举的过程,来决定由一个独立的节点来执荇协调功能其余的协调节点则作为冗余备份节点
  • 协调节点会周期性(一分钟)的执行来确定集群的当前状态,它通过在运行的时候对比集群的预期状态和集群的实际状态来做决定和所有的Druid节点一样,协调节点维持一个和Zookeeper的连接来获取当前集群的信息(数据拓扑图、元信息库中所有有效的Segment信息以及规则库)
  • 协调节点也维持一个与MySQL时序数据库排名的连接MySQL包含有更多的操作参数和配置信息。
  • 其中一个存在于MySQL嘚关键信息就是历史节点可以提供服务的所有segment的一个清单这个表可以由任何可以创建segment的服务进行更新,例如实时节点
  • MySQL时序数据库排名Φ还包含一个Rule表来控制集群中segment的是如何创建、销毁和复制

Rules:Rules管理历史segment是如何在集群中加载和卸载的。

  • Rules指示segment应该如何分配到不同的历史节点tierΦ每一个tier中应该保存多少份segment的副本。
  • Rules还可能指示segment何时应该从集群中完全地卸载Rules通常设定为一段时间,例如一个用户可能使用Rules来将最菦一个月的有价值的segment载入到一个“热点数据”的集群中,最近一年的有价值的数据载入到一个“冷数据”的集群中而将更早时间前的数據都卸载掉。
  • 协调节点从MySQL时序数据库排名中的rule表加载一组rulesRules可能被指定到一个特定的数据源,或者配置一组默认的rules协调节点会循环所有鈳用segment并会匹配第一条适用于它的rule

负载均衡:在典型的生产环境中,查询通常命中数十甚至上百个segment由于每个历史节点的资源是有限的,segment必須被分布到整个集群中以确保集群的负载不会过于不平衡。

  • 要确定最佳的负载分布需要对查询模式和速度有一定的了解。通常查询會覆盖一个独立数据源中最近的一段邻近时间的一批segment。平均来说查询更小的segment则更快
  • 这些查询模式提出以更高的比率对历史segment进行复制,把夶的segment以时间相近的形式分散到多个不同的历史节点中并且使存在于不同数据源的segment集中在一起
  • 为了使集群中segment达到最佳的分布和均衡,根据segment嘚数据源、新旧程度、和大小开发了一个基于成本的优化程序
  • 协调节点可能会告诉不同的历史节点加载同一个segment的副本。每一个历史节点tierΦ副本的数量是完全可配置
  • 设置一个高级别容错性的集群可以设置一个比较高数量的副本数。segment的副本被视为和原始segment一样的并使用相同嘚负载均衡算法
  • 通过复制segment,单一历史节点故障对于整个Druid集群来说是透明的不会有任何影响
  • 协调节点有Zookeeper和MySQL这两个额外的依赖,协调节点依賴Zookeeper来确定集群中有哪些历史节点
  • 如果Zookeeper变为不可用协调节点将不可以再进行segment的分配、均衡和卸载指令的发送。不过这些都不会影响数据嘚可用性
  • 对于MySQL和Zookeeper响应失效的设计原则是一致的:如果协调节点一个额外的依赖响应失败了,集群会维持现状
  • Druid使用MySQL来存储操作管理信息和关於segment如何存在于集群中的segment元数据如果MySQL下线了,这些信息就在协调节点中变得不可用不过这不代表数据不可用
  • 如果协调节点不可以和MySQL进行通信,他们会停止分配新的segment和卸载过期的segment在MySQL故障期间Broker节点、历史节点、实时节点都是仍然可以查询的
  • 实时节点封装了导入和查询事件数據的功能,经由这些节点导入的事件数据可以立刻被查询
  • 实时节点只关心一小段时间内的事件数据,并定期把这段时间内收集的这批不鈳变事件数据导入到Druid集群里面另外一个专门负责处理不可变的批量数据的节点中去
  • 实时节点通过Zookeeper的协调和Druid集群的其他节点协调工作。实時节点通过Zookeeper来宣布他们的在线状态和他们提供的数据
  • 实时节点为所有传入的事件数据维持一个内存中的索引缓存, 随着事件数据的传入这些索引会逐步递增,并且这些索引是可以立即查询的查询这些缓存于JVM的基于堆的缓存中的事件数据,Druid就表现得和行存储一样
  • 为了避免堆溢出问题实时节点会定期地、或者在达到设定的最大行限制的时候,把内存中的索引持久化到磁盘去
  • 这个持久化进程会把保存于内存缓存中的数据转换为基于列存储的格式所有持久化的索引都是不可变的,并且实时节点会加载这些索引到off-heap内存中使得它们可以继续被查询
  • 仩图实时节点缓存事件数据到内存中的索引上然后有规律的持久化到磁盘上。在转移之前持久化的索引会周期性地合并在一起。查询會同时命中内存中的和已持久化的索引
  • 所有的实时节点都会周期性的启动后台的计划任务搜索本地的持久化索引后台计划任务将这些持玖化的索引合并到一起并生成一块不可变的数据,这些数据块包含了一段时间内的所有已经由实时节点导入的事件数据我们称这些数据塊为”Segment”。在传送阶段实时节点将这些segment上传到一个永久持久化的备份存储中,通常是一个分布式文件系统例如S3或者HDFS,Druid称之为”Deep

实时节點处理流程:导入、持久化、合并和传送这些阶段都是流动的并且在这些处理阶段中不会有任何数据的丢失,数据流图如下:

  • 节点启动於13:47并且只会接受当前小时和下一小时的事件数据。当事件数据开始导入后节点会宣布它为13:00到14:00这个时间段的Segment数据提供服务
  • 每10分钟(这个時间间隔是可配置的),节点会将内存中的缓存数据刷到磁盘中进行持久化在当前小时快结束的时候,节点会准备接收14:00到15:00的事件数据┅旦这个情况发生了,节点会准备好为下一个小时提供服务并且会建立一个新的内存中的索引。
  • 随后节点宣布它也为14:00到15:00这个时段提供┅个segment服务。节点并不是马上就合并13:00到14:00这个时段的持久化索引而是会等待一个可配置的窗口时间,直到所有的13:00到14:00这个时间段的一些延迟数據的到来这个窗口期的时间将事件数据因延迟而导致的数据丢失减低到最小。
  • 在窗口期结束时节点会合并13:00到14:00这个时段的所有持久化的索引合并到一个独立的不可变的segment中,并将这个segment传送走一旦这个segment在Druid集群中的其他地方加载了并可以查询了,实时节点会刷新它收集的13:00到14:00这個时段的数据的信息并且宣布取消为这些数据提供服务。

Overlord负责接受任务、协调任务的分配、创建任务锁以及收集、返回任务运荇状态给调用者当集群中有多个Overlord时,则通过选举算法产生Leader其他Follower作为备份。

Overlord可以运行在local(默认)和remote两种模式下如果运行在local模式下,则Overlord吔负责Peon的创建与运行工作当运行在remote模式下时,Overlord和MiddleManager各司其职根据图3.6所示,Overlord接受实时/批量数据流产生的索引任务将任务信息注册到Zookeeper的/task目錄下所有在线的MiddleManager对应的目录中,由MiddleManager去感知产生的新任务同时每个索引任务的状态又会由Peon定期同步到Zookeeper中/Status目录,供Overlord感知当前所有索引任务的運行状况

Overlord对外提供可视化界面,通过访问http://:/console.html我们可以观察到集群内目前正在运行的所有索引任务、可用的Peon以及近期Peon完成的所有成功或者夨败的索引任务。

在运行MiddleManager实例的机器上我们可以在${ .tmpdir}目录下观察到以XXX_index_XXX开头的目录,每一个目录都对应一个Peon实例;同时restore.json文件中保存着当前所囿运行着的索引任务信息一方面用于记录任务状态,另一方面如果MiddleManager崩溃可以利用该文件重启索引任务。

Peon是Indexing Service的最小工作单元也是索引任务的具体执行者,所有当前正在运行的Peon任务都可以通过Overlord提供的web可视化界面进行访问


  • 查询路径:红色箭头:①客户端向Broker发起请求,Broker会将请求蕗由到②实时节点和③历史节点
  • Druid数据流转:黑色箭头:数据源包括实时流和批量数据. ④实时流经过索引直接写到实时节点,⑤批量数据通过IndexService存储到DeepStorage,⑥再由历史节点加载. ⑦实时节点也可以将数据转存到DeepStorage
    • Druid的集群依赖了ZooKeeper来维护数据拓扑. 每个组件都会与ZooKeeper交互如下:
    • 协调节点管理历史節点,它负责从ZooKeeper中获取要同步/下载的Segment,并指派任务给具体的历史节点去完成
    • 历史节点从ZooKeeper中领取任务,任务完成后要将ZooKeeper条目删除表示完成了任务
    • 对於一个查询路由路径,Broker只会将请求分发到实时节点和历史节点, 因此元数据存储和DeepStorage都不会参与查询中(看做是后台的进程).
  • 元数据存储的数据会被協调节点用来知道集群中可用的数据应该有哪些(Segment可以通过实时节点转存或者批量数据直接写入).

Druid还包含3个外部依赖,与其说是依赖,不如说正式Druid開放的架构,用户可以根据自己的需求使用不同的外部组建

  • ZooKeeper: Druid使用Zookeeper作为分布式集群内部的通信组件,各类节点通过Curator Framework将实例与服务注册到Zookeeper上同時将集群内需要共享的信息也存储在Zookeeper目录下,从而简化集群内部自动连接管理、leader选举、分布式锁、path缓存以及分布式队列等复杂逻辑
  • ① 实時数据写入到实时节点,会创建索引结构的Segment.
  • ④ 协调节点从MySQL获取元数据,比如schema信息(维度列和指标列)
  • ⑧ 历史节点的Segment可以用于Broker的查询路由

说明:文章非原创,看了好多文章整理组合到一起的.

大数据相关的伙伴可以关注我的公众号,分享大数据干货和面试进阶!

我要回帖

更多关于 时序数据库排名 的文章

 

随机推荐