You are viewing an old version of this page. View the current version.

Compare with Current View Page History

« Previous Version 4 Next »

1.背景

  1. 目前IoTDB主要的功能是针对时间序列的数据存储,分析,无法进行数据采集。
  2. Prometheus 提供的是一整套监控体系。(Prometheus允许用户使用他们的数据库,而不仅仅是普罗米修斯数据库来存储时间序列数据库。)
    1. 服务核心组件,通过pull metrics从Exporter拉取和存储监控数据,并提供一套灵活的查询语言(PromQL)
    2. pushgateway:类似于一个中转站,Prometheus Server只会通过pull方式拉取数据但是某些节点因为某些原因只能通过Push方式推送数据,这个时候就需要pushgateway了,它负责的是接收push来的数据并暴露给Prometheus Server,以待其拉取。
    3. Exporters/Jobs:负责收集目标对象(host,container...)的性能数据,并通过HTTP接口供Prometheus Server获取
    4. Service Discovery:服务发现,Prometheus支持多种服务发现机制:文件,DNS,Consul,Kubernetes,OpenStack,EC2等等,基于服务发现的过程并不复杂,通过第三方提供的接口,Prometheus查询到需要监控的Target列表,然后轮询这些Target获取监控数据。
    5. Alertmanager:从Prometheus Server端接收到alerts后,会进行去除重复数据,分组,并路由到对方的接收方式,发出警报,常见的接收方式有电子邮件,pagerduty等

2.目标

IoTDB集成Prometheus,实现IoTDB针对时间序列的数据采集。完善IoTDB的功能。

可以看到,Prometheus向IoTDB中写入数据通过中间件,Prometheus读取IoTDB的数据也通过中间件,中间件的主要作用是将Prometheus格式的数据和IoTDB所需格式的数据相互转换。

  1. IoTDB-Prometheus:实现Prometheus和IoTDB之间的模式映射将Prometheus的metric {label1="label1_value",label2="label2_value"}映射到时序
  2. 对正确性和性能的测试,不仅要集成Prometheus,也要知道在繁重的负载下是否可以很好的工作,例如:以非常高的频率生成数据
    1. 性能测试:Avalanche Code: https://github.com/open-fresh/avalanche
      支持通过Prometheus remote_write API接受数据的服务的负载测试,进行性能测试,
    2. 正确性测试:Prombench,Code: https://github.com/ncabatoff/prombench
      向Prometheus插入数据,然后查询Prometheus,将我们认为发送的内容与我们希望存储的内容进行比较。进行正确性测试

3.设计(前提:IoTDB Go Client)

3.1 配置Prometheus 远程存储

在Prometheus配置文件中配置远程存储的地址(由IoTDB-Prometheus提供)

eg:

3.2 IoTDB-Prometheus(接收Prometheus传输过来的数据/查询IoTDB中数据) 

IoTDB-Prometheus为外部go服务,使用go语言编译器编译生成可执行文件

  1. 前提

    1. Golang编译器

    2. 包含go-client的IoTDB

  2. Prometheus读取和写入远程存储都是通过HTTP协议,将数据以snappy方式压缩到协议缓冲区中

  3. IoTDB-Prometheus获取传输过来的数据,进行解压缩,反序列化,转化为IoTDB的数据格式(需要实现的)

  4. 调用go-client和IoTDB服务端进行数据交互(需要实现的)

3.3 将Prometheus的数据格式转成成IoTDB的数据格式

3.3.1问题

  1. 问题:Prometheus中label顺序不敏感,而在IoTDB中是敏感的

    1. Prometheus的时序构成

      1. metric name

      2. label key

      3. label value

    2. IoTDB的时序构成:

      1. storage group

      2. path(time series ID)

      3. measurement

    3. 在Prometheus中,使用一个metric和label的集合代表一条时间序列,label的顺序不影响

      eg:'host = server1, data_center = DC1` 和 `data_center = DC1, host = server1`相等。

    4. 在IoTDB中

      1. 一个path由多个部分组成,比如`root.sg1.DC1.server1` 由一个存储组 `root.sg1`和两个节点`DC1` 和`server1`构成

      2. 节点的顺序是需要考虑的,`root.sg1.DC1.server1` 和 `root.sg1.server1.DC1` 是两条不同的时序。

  2. 关键点:需要记录每个label对应的顺序,确保Prometheus中label顺序不同的同一条时序对应到IoTDB中也是一条时序

  3. 需要解决的事情

    1. 怎样映射label key和它对应的order
    2. 在不知道所有的label key的情况下,怎么维护他们之间的顺序

3.3.2 解决方案

  1. 主要思想:
    1. 内存中Map <Metric, Map <Label Key, Order> > table结构维护label之间的顺序
    2. Prometheus中时序根据label顺序对应到IoTDB
  2. 实例
    1. 添加时序
      1.  Prometheus时序: 

        (1)country{state=A,city=B,town=C}

        (2)country{tem=D}

        (3))country{state=A,city=B,town=C,tem=D}  

      2. 假设存储组数量为5,则("country").hashCode() % 5为2,对应的存储组为sg2,测点为country
      3.  (1)对应的记录label顺序的table为

        metric_name 
        label_key 
        order 
        country
        state
        0
        country
        city
        1
        country
        town
        2

         (2)对应的记录label顺序的table为 

        metric_name 
        label_key 
        order 
        country
        state
        0
        country
        city
        1
        country
        town
        2
        country
        tem3

        (3)对应的记录label顺序的table为

        metric_name 
        label_key 
        order 
        country
        state
        0
        country
        city
        1
        country
        town
        2
        country
        tem3
      4. (1)对应IoTDB时序为root.sg2.A.B.C.country 

        (2)对应IoTDB时序为root.sg2.ph.ph.ph.D.country 

        (3)对应IoTDB时序为root.sg2.A.B.C.D.country 

      5. 为了重启时候对table的恢复,在IoTDB中记录数据

        root.LABEL_INFO.metric_name
        root.LABEL_INFO.label_name
        root.LABEL_INFO.label_order
        country 
        state 
        0
        country
        city
        1
        country
        town
        2
        country
        tem3
    2. 查询数据
      1. 查询数据:查询country中city=B的数据,city的order为1,country中order的最大值为3

        1. 对应到IoTDB中的查询为

          1. select country from root.sg0.*.B

          2. select country from root.sg0.*.B.*

          3. select country from root.sg0.*.B.*.*

  3. 设计
    1. 允许用户设置IoTDB中SG的数量,例如,`SG_NUMBER`=5。可以是`iotdb-engine.properties`中的参数.然后得到5个sg,比如“sg0,sg1,…,sg4”。

    2. metric

      1. 认为是IoTDB中的一个measurement

      2. 可以通过hash决定metric会对应到哪个存储组,eg Metric.hashcode() % SG_NUMBE‘

    3. 在内存中维护一个table去保存对应的映射,在内存中的结构为:Map <Metric, Map <Label Key, Order> > table(改进:考虑到内存开销,可以只将表的一部分作为缓存保存在内存中)------- 解决问题:怎样映射label key和它对应的order

    4. 在IoTDB中存储metric,label以及其对应的顺序,通过三条时序(以便在IoTDB重启的时候恢复内存中的table)

      1. 'root.system_p.label_info.metric_name'

      2. root.system_p.label_info.label_name'

      3. 'root.system_p.label_info.label_order`
    5. 添加metric时维护map ------------ 解决问题:在不知道所有label的情况下维护map

      1. 首先判断table.get(metric_name)为空,则向时序'root.LABEL_INFO.metric_name'中添加数据点,时间戳可以是系统当前的时间或者是0,1,2,3,value是metric name,同时在table中添加对应的metric

      2. 其次根据metric_name,label_key判断table.get(metric_name).get(label_key)为空,则向时序'root.system_p.label_info.label_name'中添加数据点,时间戳可以是系统当前的时间或者是0,1,2,3,value是label_key

        同时也要向时序'root.system_p.label_info.label_order`中添加数据点,时间戳和对应的'root.system_p.label_info.label_name'中添加的数据点的时间戳相同,但是value是对应的metric中的最大的order+1

        table.get(metric_name)中添加对应的label_key和lable_order.

    6. 生成IoTDB对应的时序

      1. string paths[]数组记录时序节点,int  largest记录metric中label的order的最大值
      2. 已有的label,paths[label_order]=label_value
      3. 新的label,paths[largest+1]=label_value
      4. 遍历paths数组,null的位置填充ph,得到时序root+sg_name+paths.sub(0, paths.size()-1).metric

3.4 参考文档

  1. https://docs.google.com/document/d/1UYOUd0YomS6NUitG9Ko0gqzYapn6eqhFuy_5F3NKVxg/edit#heading=h.mdfygy3ywxxh
  2. https://docs.google.com/document/d/1DZL1L0GccLvHbMJyop62cbaSvu1tkJ6Pp1Fp6FsR09U/edit#heading=h.58lkrsg45cf2
  3. https://issues.apache.org/jira/projects/IOTDB/issues/IOTDB-519?filter=allopenissues&orderby=cf%5B12310310%5D+ASC%2C+priority+DESC%2C+updated+DESC
  4. https://prometheus.io/docs/prometheus/latest/storage/
  5. https://songjiayang.gitbooks.io/prometheus/content/exporter/text.html
  6. https://www.taosdata.com/cn/documentation/insert/#Prometheus%E7%9B%B4%E6%8E%A5%E5%86%99%E5%85%A5
  • No labels