云智慧 AIOps 社区是由云智慧发动,针对运维业务场景,提供算法、算力、数据集整体的服务体系及智能运维业务场景的解决方案交换社区。该社区致力于流传 AIOps 技术,旨在与各行业客户、用户、研究者和开发者们独特解决智能运维行业技术难题,推动 AIOps 技术在企业中落地,建设衰弱共赢的 AIOps 开发者生态。
智能运维畛域的数据特点
指标数据作为运维场景中的重要观测项,是服务可用性监控、零碎衰弱度度量等场景的次要数据起源。从上面架构示意图中们能够看出,采集器采集服务器上各种指标数据,发往音讯队列,通过实时流解决和离线计算最终存入到数据库。
在这个上述场景中,咱们往往会遇到以下几种数据挑战:
- 咱们日常须要监控的指标数量超百万,峰值时甚至会达到千万级,每天积淀下来的指标数据量达到 GB 级别,甚至 TB 级别。
- 针对指标数据的日常剖析行为通常波及到近 1 小时、近 1 天、近 7 天、近 30 天、近 1 年等多种时间跨度。对范畴查问的性能有肯定要求。
3)在数据传输过程中,因为受到网络、设施资源等起因造成短时间内呈现乱序达到、缺丢点、峰谷潮、反复数据等问题
4)因为服务器或设施自身起因,采集的指标数据工夫往往不够精准,导致数据粒度不齐整的问题。例如对于秒级别的指标,上一个采集的数据点的工夫戳是 2021-01-01 10:00:00:000 下一个数据点的有可能是 2021-01-01 10:00:01:015。而不同的指标雷同时刻采集的数据点工夫戳别离是 2021-01-01 10:00:00:000 和 2021-01-01 10:00:00:015。
至此整体的需要根本曾经明确,在做数据库选型时须要满足以下需要:
1)反对数据长时间存储;
2)反对大时间跨度的疾速检索;
3)高速的数据吞吐能力;
4)高效的数据压缩比;
5)可能无效的解决数据的乱序、缺失值、粒度不齐整以及反复数据等数据品质问题。
智能运维畛域的时序数据该如何存储
对于上述的需要咱们该如何选型?是传统的关系型数据库,还是通用的 NoSQL 数据库,亦或是专用的时序数据库?他们是否满足上述数据库选型的需要?
数据如何存储还要联合数据自身的特点。这里以一个实在场景中的案例,某运营商有约 3000 万的监控指标,并且采集的过程中存在空值数据、数据缺失、数据反复等状况,甚至会呈现新的指标。如果一分钟采集一次指标在容许肯定数据提早的状况下,写入速率要超过 50w/s,一天须要存储 432 亿的数据,这对关系数据库来说无论是从写入速率是在查问时效都很难满足需要。
再看看通用的 NoSQL 数据库,首先先简略梳理一下这些指标数据的特点,咱们发现这些指标数据除了有工夫戳和指标值外还会有一些 tag 来标识数据来自那台机器,通过采集器理论的采集数据的样例如下图所示:
在通用的 NoSql 数据库尽管能够满足吞吐量性能以及查问性能,然而为了满足指标的动静变更咱们只能依照一个设施一张表或者多个设施共享一张表的建模形式如下图所示。
无论是一个设施一张表还是多个设施共享一张表的存储形式,为了可能辨别数据来哪个指标,咱们只能把 tags 作为一列进行存储,不难发现这种这样建表形式会呈现大量的 tag 数据冗余存储的问题。并且通用的 NoSql 数据库往往在解决数据反复的问题上并不敌对,更多的是依附一些排重策略来实现。排重策略通常有两种:一种是依附内部的排重形式达到存储时数据曾经排重,另一种是存储不排除查问时依附 sql 来做排重。如果应用第一种数据排重无疑会减少零碎的复杂度,如果应用第二种这会导致在处理过程的呈现数据冗余存储的状况。而且通用的 NoSql 数据库还存在一个问题就是:没有原生操作反对粒度卡齐或者线性填充来解决数据品质差的问题。
然而咱们下面的遇到的一些数据挑战理论是属于时序数据库要解决的典型问题,市面上也有许多优良的时序数据库,例如 InfluxDB、Apache IoTDB 等,它们在高吞吐、低延时查问、数据去重、数据填充、数据降采样、高压缩比等性能方面皆能满足第一章中的数据存储需要。接下来咱们来重点看下齐全开源的 Apache IoTDB 它是如何设计的。
IoTDB 的设计
IoTDB 的架构
IoTDB 是基于 LSM-Tree(Log-Structured Merge Tree)的架构进行设计的列式存储数据库,LSMtree 的核心思想就是放弃局部读的能力来换取最大的写入能力。从下图中 IoTDB 的整体架构图中咱们能够看出 IoTDB 次要有三局部形成:别离是数据库引擎、存储引擎和剖析引擎。
数据库引擎次要是负责 sql 语句的解析、数据写入、数据查问、数据删除等性能。
存储引擎次要是由 TsFile 来组成也是 IoTDB 的最具特色的设计,它不仅能够为 IoTDB 存储引擎应用,而且还能够间接通过链接器供剖析引擎应用,同时还对外开放了 TsFile 的 API,用户也能够本人间接通过 API 来获取外面的内容。
剖析引擎次要是用于与开源的数据处理平台对接等。
IoTDB 的数据读写流程
下面提到了 IoTDB 是基于 LSM-Tree 的思维来实现的,从以下数据写入流程图中咱们能够看出:数据通过 time detector 时会依据内存中保护的最大工夫戳来判断是否数据有序,在内存缓冲区 memtable 中分为有序序列和乱序序列,同时为了保障在断电后数据不失落,IoTDB 也会把数据写入到 WAL(Write-Ahead Logging)中,到此客户端的数据写入就曾经实现。随着数据的一直写入,memtable 中的数据达到肯定的水平后,IoTDB 通过 submit flush task 把 memtable 变成 Immutable 最终刷到磁盘变成 Sstable 即 TsFile 文件,同时当长久化的 TsFile 文件达到肯定水平会触发合并。
下面介绍了 IoTDB 数据的写入流程后,咱们再来看下 IoTDB 外围的查问流程。如下图所示,当客户端发送查问申请时,首先通过 Antlr4 进行 sql 解析,而后去内存中的 MemTable、ImmuTable 和硬盘中 TsFile 中进行查问。当然,IoTDB 这里会通过 BloomFilter 和索引来进步数据的查问效率。咱们晓得 BloomFilter 的原理是哈希后果不存在那么肯定没有此数据,如果哈希后果存在,IoTDB 那么还须要持续借助索引进行进一步的查找。
TsFile 构造
上一节 IoTDB 的读写流程都离不开 TsFile,那咱们看看 IoTDB 最外围 TsFile 是怎么一个构造。从上面的 TsFile 构造示意图中能够看出 TsFile 整体分为两局部:一部分是数据区,另一部分是索引区。
数据区次要包含 Page 数据页、Chunk 数据块和 ChunkGroup 数据组。其中 Page 由一个 PageHeader 和一段数据 (time-value 编码的键值对) 组成,Chunk 数据块由多个 Page 和一个 Chunk Header 组成,ChunkGroup 存储了一个实体(Entity) 一段时间的数据,它由若干个 Chunk, 一个字节的分隔符 0x00 和一个 ChunkFooter 组成。
索引区次要包含 TimeseriesIndex、IndexOfTimeseriesIndex 和 BloomFilter,其中 TimeseriesIndex 蕴含 1 个头信息和数据块索引(ChunkIndex)列表,头信息记录文件内某条工夫序列的数据类型、统计信息(最大最小工夫戳等);数据块索引列表记录该序列各 Chunk 在文件中的 offset,并记录相干统计信息(最大最小工夫戳等);IndexOfTimeseriesIndex 用于索引各 TimeseriesIndex 在文件中的 offset;BloomFilter 针对实体(Entity)的布隆过滤器。下图中 TsFile 包含两个实体 d1、d2,每个实体别离蕴含三个物理量 s1、s2、s3,共 6 个工夫序列,每个工夫序列蕴含两个 Chunk。
TsFile 索引构建
TsFile 中所有的索引节点形成一棵类 B + 树结构的多叉索引树,这棵树由两局部组成:实体索引局部和物理量索引局部。上面举一个例子来展现索引树的形成:假如咱们设置树的度为 10,咱们有 150 个设施每个设施有 150 个测点共计 22500 条工夫序列,这时咱们需构建一个深度为 6 的索引树即可,这时咱们查问数据所在位置需做 6 次磁盘的 IO,具体如下图所示。
下面这种形式看似磁盘 IO 次数比拟多,这是因为咱们设置的树的度比拟小从而导致整体树的深度比拟大。如果咱们把树的度增大到 300,在实体索引局部一个高度为 2 的子树即可实现 90000 个设施存储,同理一个高度为 2 个物理量索引局部也可寄存 90000 个物理量,最终造成的整个索引树可寄存 81 亿条工夫序列。这时咱们再读取数据只须要做 4 次磁盘 IO 即可定位到咱们须要的数据地位。
TsFile 查问流程
在理解了 TsFile 的构造以及索引的构建,那么 IoTDB 是如何在 TsFile 外部实现一次查问的,上面用一个具体查问例如 select s1 from root.ln.d1 where time>100 and time<200,来演示在 TsFile 中是如何定位到所需数据。他的具体步骤以及示意图如下所示:
1)读取 TsFile MetadataSize 信息
2)依据 TsFile MetadataSize 和 offset 获取 TsFile MetaData 的地位
3)读取 Metadata IndexNode 中的数据,通过 MetadataIndexEntry 中的 name 定位到设施 root.ln.d1
4)读取到设施 root.ln.d1 中的 offset 偏移量,依据偏移量找到 TimeSeries Metadata 中的信息进而找到 s1
5)通过 ChunkMetadata 记录的统计信息 startTime 和 endTime 与咱们查问的区间(100,200)比照获取到 root.ln.d1 设施上面测点 s1 的偏移量
6)依据 s1 中的偏移量能够间接获取到 ChunkGroup
7)顺次通过 ChunkGroupHeader、ChunkHeader 定位到 Chunk 数据顺次读取 Page 中的 PageHeader,如果工夫区间在(100,200)中那么咱们就间接读取 PageData 数据。
总结
本文抛砖引玉简略的介绍了 IoTDB 的读写以及 TsFile 的外围文件的设计,实际上 IoTDB 整体设计和实现还是比拟杂,外面波及了很多的细节这里就不再开展介绍了。
写在最初
近年来,在 AIOps 畛域疾速倒退的背景下,IT 工具、平台能力、解决方案、AI 场景及可用数据集的迫切需要在各行业爆发。基于此,云智慧在 2021 年 8 月公布了 AIOps 社区, 旨在树起一面开源旗号,为各行业客户、用户、研究者和开发者们构建沉闷的用户及开发者社区,独特奉献及解决行业难题、促成该畛域技术倒退。
社区先后 开源 了数据可视化编排平台 -FlyFish、运维治理平台 OMP 、云服务治理平台 - 摩尔平台、 Hours 算法等产品。
可视化编排平台 -FlyFish:
我的项目介绍:https://www.cloudwise.ai/flyF…
Github 地址:https://github.com/CloudWise-…
Gitee 地址:https://gitee.com/CloudWise/f…
行业案例:https://www.bilibili.com/vide…
局部大屏案例:
请您通过上方链接理解咱们,增加小助手(xiaoyuerwie)备注:飞鱼。退出开发者交换群,可与业内大咖进行 1V1 交换!
也可通过小助手获取云智慧 AIOps 资讯,理解云智慧 FlyFish 最新进展!