`
yuun
  • 浏览: 58529 次
文章分类
社区版块
存档分类
最新评论

时间序列数据的存储和计算 - 开源时序数据库解析(一)

 
阅读更多

摘要: 开源时序数据库   如图是17年6月在db-engines上时序数据库的排名,我会挑选开源的、分布式的时序数据库做详细的解析。前十的排名中,RRD是一个老牌的单机存储引擎,Graphite底层是Whisper,可以认为是一个优化的更强大的RRD数据库。

开源时序数据库

image

  如图是17年6月在db-engines上时序数据库的排名,我会挑选开源的、分布式的时序数据库做详细的解析。前十的排名中,RRD是一个老牌的单机存储引擎,Graphite底层是Whisper,可以认为是一个优化的更强大的RRD数据库。kdb+、eXtremeDB和Axibase都未开源,不做解析。InfluxDB开源版和Prometheus的底层都是基于levelDB自研的单机的存储引擎,InfluxDB的商业版支持分布式,Prometheus的roadmap上也规划了分布式存储引擎的支持计划。
  综合看下来,我会选择OpenTSDB、KairosDB和InfluxDB做一个详细的解析。我对OpenTSDB比较熟悉,研究过它的源码,所以对OpenTSDB会描述的格外详细,而对其他时序数据库了解的没那么深入,如果有描述错的地方,欢迎指正。

OpenTSDB

  OpenTSDB是一个分布式、可伸缩的时序数据库,支持高达每秒百万级的写入能力,支持毫秒级精度的数据存储,不需要降精度也可以永久保存数据。其优越的写性能和存储能力,得益于其底层依赖的HBase,HBase采用LSM树结构存储引擎加上分布式的架构,提供了优越的写入能力,底层依赖的完全水平扩展的HDFS提供了优越的存储能力。OpenTSDB对HBase深度依赖,并且根据HBase底层存储结构的特性,做了很多巧妙的优化。关于存储的优化,我在这篇文章中有详细的解析。在最新的版本中,还扩展了对BigTable和Cassandra的支持。

架构

image
  如图是OpenTSDB的架构,核心组成部分就是TSD和HBase。TSD是一组无状态的节点,可以任意的扩展,除了依赖HBase外没有其他的依赖。TSD对外暴露HTTP和Telnet的接口,支持数据的写入和查询。TSD本身的部署和运维是很简单的,得益于它无状态的设计,不过HBase的运维就没那么简单了,这也是扩展支持BigTable和Cassandra的原因之一吧。

数据模型

  OpenTSDB采用按指标建模的方式,一个数据点会包含以下组成部分:

  • metric:时序数据指标的名称,例如sys.cpu.user,stock.quote等。
  • timestamp:秒级或毫秒级的Unix时间戳,代表该时间点的具体时间。
  • tags:一个或多个标签,也就是描述主体的不同的维度。Tag由TagKey和TagValue组成,TagKey就是维度,TagValue就是该维度的值。
  • value:该指标的值,目前只支持数值类型的值。

存储模型

  OpenTSDB底层存储的优化思想,可以参考这篇文章,简单总结就是以下这几个关键的优化思路:

  • 对数据的优化:为Metric、TagKey和TagValue分配UniqueID,建立原始值与UniqueID的索引,数据表存储Metric、TagKey和TagValue对应的UniqueID而不是原始值。
  • 对KeyValue数的优化:如果对HBase底层存储模型十分了解的话,就知道行中的每一列在存储时对应一个KeyValue,减少行数和列数,能极大的节省存储空间以及提升查询效率。
  • 对查询的优化:利用HBase的Server Side Filter来优化多维查询,利用Pre-aggregation和Rollup来优化GroupBy和降精度查询。

UIDTable

  接下来看一下OpenTSDB在HBase上的几个关键的表结构的设计,首先是tsdb-uid表,结构如下:

image

Metric、TagKey和TagValue都会被分配一个相同的固定长度的UniqueID,默认是三个字节。tsdb-uid表使用两个ColumnFamily,存储了Metric、TagKey和TagValue与UniqueID的映射和反向映射,总共是6个Map的数据。

从图中的例子可以解读出:

  • TagKey为'host',对应的UniqueID为'001'
  • TagValue为'static',对应的UniqueId为'001'
  • Metric为'proc.loadavg.1m',对应的UniqueID为'052'

  为每一个Metric、TagKey和TagValue都分配UniqueID的好处,一是大大降低了存储空间和传输数据量,每个值都只需要3个字节就可以表示,这个压缩率是很客观的;二是采用固定长度的字节,可以很方便的从row key中解析出所需要的值,并且能够大大减少Java堆内的内存占用(bytes相比String能节省很多的内存占用),降低GC的压力。
  不过采用固定字节的UID编码后,对于UID的个数是有上限要求的,3个字节最多只允许有16777216个不同的值,不过在大部分场景下都是够用的。当然这个长度是可以调整的,不过不支持动态更改。

DataTable

第二张关键的表是数据表,结构如下:

image

  该表中,同一个小时内的数据会存储在同一行,行中的每一列代表一个数据点。如果是秒级精度,那一行最多会有3600个点,如果是毫秒级精度,那一行最多会有3600000个点。
  这张表设计的精妙之处在于row key和qualifier(列名)的设计,以及对整行数据的compaction策略。row key格式为:

<metric><timestamp><tagk1><tagv1><tagk2>tagv2>...<tagkn><tagvn>

  其中metric、tagk和tagv都是用uid来表示,由于uid固定字节长度的特性,所以在解析row key的时候,可以很方便的通过字节偏移来提取对应的值。Qualifier的取值为数据点的时间戳在这个小时的时间偏差,例如如果你是秒级精度数据,第30秒的数据对应的时间偏差就是30,所以列名取值就是30。列名采用时间偏差值的好处,主要在于能大大节省存储空间,秒级精度的数据只要占用2个字节,毫秒精度的数据只要占用4个字节,而若存储完整时间戳则要6个字节。整行数据写入后,OpenTSDB还会采取compaction的策略,将一行内的所有列合并成一列,这样做的主要目的是减少KeyValue数目。

查询优化

  HBase仅提供简单的查询操作,包括单行查询和范围查询。单行查询必须提供完整的RowKey,范围查询必须提供RowKey的范围,扫描获得该范围下的所有数据。通常来说,单行查询的速度是很快的,而范围查询则是取决于扫描范围的大小,扫描个几千几万行问题不大,但是若扫描个十万上百万行,那读取的延迟就会高很多。
  OpenTSDB提供丰富的查询功能,支持任意TagKey上的过滤,支持GroupBy以及降精度。TagKey的过滤属于查询的一部分,GroupBy和降精度属于对查询后的结果的计算部分。在查询条件中,主要的参数会包括:metric名称、tag key过滤条件以及时间范围。上面一章中指出,数据表的rowkey的格式为:<metric><timestamp><tagk1><tagv1><tagk2>tagv2>...<tagkn><tagvn>,从查询的参数上可以看到,metric名称和时间范围确定的话,我们至少能确定row key的一个扫描范围。但是这个扫描范围,会把包含相同metric名称和时间范围内的所有的tag key的组合全部查询出来,如果你的tag key的组合有很多,那你的扫描范围是不可控的,可能会很大,这样查询的效率基本是不能接受的。

我们具体看一下OpenTSDB对查询的优化措施:

  • Server side filter
    HBase提供了丰富和可扩展的filter,filter的工作原理是在server端扫描得到数据后,先经过filter的过滤后再将结果返回给客户端。Server side filter的优化策略无法减少扫描的数据量,但是可以大大减少传输的数据量。OpenTSDB会将某些条件的tag key filter转换为底层HBase的server side filter,不过该优化带来的效果有限,因为影响查询最关键的因素还是底层范围扫描的效率而不是传输的效率。

  • 减少范围查询内扫描的数据量
    要想真正提高查询效率,还是得从根本上减少范围扫描的数据量。注意这里不是减小查询的范围,而是减少该范围内扫描的数据量。这里用到了HBase一个很关键的filter,即FuzzyRowFilter,FuzzyRowFilter能够根据指定的条件,在执行范围扫描时,动态的跳过一定数据量。但不是所有OpenTSDB提供的查询条件都能够应用该优化,需要符合一定的条件,具体要符合哪些条件就不在这里说明了,有兴趣的可以去了解下FuzzyRowFilter的原理。

  • 范围查询优化成单行查询
    这个优化相比上一条,更加的极端。优化思路非常好理解,如果我能够知道要查询的所有数据对应的row key,那就不需要范围扫描了,而是单行查询就行了。这里也不是所有OpenTSDB提供的查询条件都能够应用该优化,同样需要符合一定的条件。单行查询要求给定确定的row key,而数据表中row key的组成部分包括metric名称、timestamp以及tags,metric名称和timestamp是能够确定的,如果tags也能够确定,那我们就能拼出完整的row key。所以很简单,如果要能够应用此优化,你必须提供所有tag key对应的tag value才行。

  以上就是OpenTSDB对HBase查询的一些优化措施,但是除了查询,对查询后的数据还需要进行GroupBy和降精度。GroupBy和降精度的计算开销也是非常可观的,取决于查询后的结果的数量级。对GroupBy和降精度的计算的优化,几乎所有的时序数据库都采用了同样的优化措施,那就是pre-aggregation和auto-rollup。思路就是预先进行计算,而不是查询后计算。不过OpenTSDB在已发布的最新版本中,还未支持pre-aggregation和rollup。而在开发中的2.4版本中,也只提供了半吊子的方案,它只提供了一个新的接口支持将pre-aggregation和rollup的结果进行写入,但是对数据的pre-aggregation和rollup的计算还需要用户自己在外层实现。

总结

  OpenTSDB的优势在于数据的写入和存储能力,得益于底层依赖的HBase所提供的能力。劣势在于数据查询和分析的能力上的不足,虽然在查询上已经做了很多的优化,但是不是所有的查询场景都能适用。可以说,OpenTSDB在TagValue过滤查询优化,是这次要对比的几个时序数据库中,优化的最差的。在GroupBy和Downsampling的查询上,也未提供Pre-aggregation和Auto-rollup的支持。不过在功能丰富程度上,OpenTSDB的API是支持最丰富的,这也让OpenTSDB的API成为了一个标杆。

原文链接:http://click.aliyun.com/m/28595/

分享到:
评论

相关推荐

    时序数据库LinDB架构演进.zip

    时序数据库,作为一种专门处理时间序列数据的数据库类型,近年来在物联网、监控系统、金融交易等领域得到了广泛应用。其中,LinDB是一款开源的时序数据库,以其高效、稳定的特点深受业界青睐。本文将深入探讨LinDB的...

    timescaledb-postgresql-12_1.7.1-windows-amd64.zip

    在实际应用中,TimescaleDB通过创建时间维度的分片(chunks)来高效存储和查询时间序列数据,可以使用SQL标准语法进行复杂的时序分析。例如,创建一个时间序列表: ```sql CREATE TABLE measurements ( time ...

    timescaledb-postgresql-13_2.3.0-windows-amd64.zip

    TimescaleDB是一款针对时间序列数据设计的开源数据库扩展,它构建于PostgreSQL之上,提供了高效的时间序列管理和分析功能。在“timescaledb-postgresql-13_2.3.0-windows-amd64.zip”这个压缩包中,包含了Timescale...

    influxdb-1.7.1_linux_amd64.tar.gz

    《InfluxDB:分布式时序数据库的深度解析》 InfluxDB是一款专为时间序列数据设计的开源数据库,尤其在监控、物联网(IoT)、性能指标和日志记录等领域表现出色。它由InfluxData公司开发,以高效处理大量时间戳数据而...

    MySQL数据库基础及技术演进.pptx

    - 时序搜索:针对时间序列数据,其他专门的时序数据库可能更优。 MySQL的技术演进伴随着数据库领域的快速发展,包括引入新的存储引擎、支持更多高级特性(如分区、视图、存储过程)以及优化的复制和集群解决方案。...

    建设DevOps统一运维监控平台.docx

    系统监控技术栈包括数据采集(主动采集和客户端采集)、数据缓冲(如消息队列)和数据存储(时序数据库,如InfluxDB和OpenTSDB)。主动采集利用SNMP、SSH等技术远程收集数据,客户端采集则在被监控节点部署agent。...

    QT操作influxdb

    QT操作InfluxDB主要涉及到...总的来说,结合QT Creator和libcurl,开发者可以轻松地构建一个与InfluxDB交互的应用,实现时间序列数据的存储、查询和分析。通过深入理解和实践这些知识点,可以构建出高效、稳定的系统。

    建设DevOps统一运维监控平台.pdf

    数据存储方面,时序数据库如InfluxDB和OpenTSDB用于存储时间序列数据,适用于大规模、高频率的监控数据存储。 三、开源监控软件对比 文档提到了Zabbix、Nagios和Open-Falcon这三款开源监控软件的对比,但具体对比...

    开源项目-influxdata-arrow.zip

    总结,InfluxData对Apache Arrow的Go语言实现是大数据处理领域的一次创新尝试,它将列式存储的高效性和Go语言的便捷性相结合,为时序数据分析提供了新的解决方案。开发者可以利用这一技术提升他们的系统性能,处理更...

    边缘计算和云计算的融合实践.pdf

    时间序列数据库(Time-series DB)、IoT Hub和流式计算(Stream Compute)用于高效处理和分析这些数据。例如,边缘视频监控平台和边缘媒体云方案利用流媒体解析和AI推断,实现实时视频分析和智能识别。 此外,边缘...

    influx-proxy-2.5.7-linux-amd64.tar.gz

    InfluxDB是一款专为时间序列数据设计的开源数据库,尤其在监控、物联网(IoT)、性能指标和其他大数据领域有着广泛的应用。而"Influx-proxy"则可能是一个针对InfluxDB的代理服务,用于优化数据流入和查询效率。本文将...

    rrdtool源码

    RRDtool(Round Robin Database Tool)是由Tobi Oetiker开发的一款开源工具,用于创建、维护和查询时序数据的圆形缓冲数据库。RRDtool的核心特性在于其高效地存储和处理时间序列数据的能力,广泛应用于监控系统、...

    解决了IoTDB第一值为null取最近一个有值的记录值返回的bug

    在物联网(IoT)数据存储领域,IoTDB是一个重要的开源时序数据库系统,专为大规模时间序列数据处理而设计。本次更新针对IoTDB的一个关键问题进行了修复,即当查询的第一个值为null时,系统无法正确返回最近一个非null...

    全国自考软件开发工具试题及答案.docx

    - **答案解析**:关键路线图主要用于项目管理和时间规划,并不属于软件开发工具的概念模式。 #### 3. 发展潜力最差的选项 - **知识点**:这里讨论的是语言及其开发工具的发展趋势。 - A.VC (Visual C++):虽然较为...

    prometheus-api数据采集

    Prometheus 是一个开源的监控和警报系统,广泛应用于云原生环境,它以其强大的时序数据处理能力和灵活的查询语言 Prometheus Query Language ( PromQL ) 而闻名。本篇文章将详细探讨如何通过 Prometheus 的 API 进行...

    influxdb-master

    InfluxDB是由InfluxData公司开发的一款开源时间序列数据库,它的设计目标是处理大量时序数据,如传感器数据、网络流量、日志条目等。其特性包括高效写入、快速查询、内置的数据聚合功能,以及对时序数据的优化存储...

    建设DevOps统一运维监控平台.doc

    6. InfluxDB:高性能的时间序列数据库,适用于存储和查询监控数据。 7. Prometheus:强大的时序数据库和监控解决方案,特别适合容器化环境,支持复杂的查询语言和规则引擎。 三、容器时代的监控 在Kubernetes(k8...

    Moth-开源

    2. **RRD 文件**:RRD 是一种用于存储时序数据的高效数据库,常用于监控系统性能。Moth 能够直接读取RRD文件,提取时间序列数据并转化为图形,这对于监控和分析系统的趋势非常有用。 3. **MySQL 数据库**:作为广泛...

    kafka+storm+influxdb的程序demo

    **InfluxDB** 是专为时间序列数据设计的数据库,特别适合存储和查询监控、日志和物联网(IoT)等场景下的数据。在本示例中,InfluxDB可能是最终的数据存储层,接收Storm处理后的结果,以便进行实时查询和分析。它的...

Global site tag (gtag.js) - Google Analytics