存储空间降为 MySQL 的十分之一,TDengine 在货拉拉数据库监控场景的应用

2022-03-21 00:00:00 数据 数据存储 监控 采样 改造

目前 DBA 团队管理的数据存储包括 MySQL、Redis、Elasticsearch、Kafka、MQ、Canal 等,为了保证监控采样的实时性,我们自研的监控系统设置的采样间隔为 10 秒,这样每天都会产生庞大的监控数据,监控指标的数据量达到 20 亿+。前期由于管理实例少,监控数据量也少,所有数据都被存放到了 MySQL 中;之后随着管理实例越来越多,使用 MySQL 来存储规模日益庞大的监控数据越发力不从心,急需进行升级改造。结合实际具体需求,通过对不同时序数据库进行调研,终我们选择了 TDengine,顺利完成了数据存储监控的升级改造。


一、监控系统开发中遇到的问题


从存储路径来看,每种数据存储都分布在多个区域,每个区域将监控采样数据投递上报到消息总线,然后由消费程序统⼀消费,消费程序会将必要的告警数据更新到告警表,同时将监控原始数据存储到 MySQL。比如,针对 Redis 这款数据存储,监控采样间隔设置 10 秒,那么每天实例采样次数就会达到 3000 万+,监控指标累计 6 亿+,数据量之庞大可见一斑。早期为了将数据存储到 MySQL 中,同时也能很好地支持监控绘图的使用,每⼀次实例监控采样时都会计算出该实例全量监控项采样数据,然后将本次采样的结果作为⼀条记录存储下来。



即使通过这样的优化处理,在做时间跨度大的监控绘图时,前端依然会出现延迟卡顿的问题,后端监控数据存储的 MySQL 也压力山大,经常满载,天天被吐槽。因此针对这种时间跨度大的查询,我们专门开发了⼀系列的数据聚合调度任务——按照不同的时间跨度,提前将 10 秒采集间隔的监控数据做好聚合,监控绘图程序再根据不同的时间跨度选取不同的聚合数据表绘图,以此解决长时间跨度监控绘图展示延迟卡顿的问题。


但这仍然治标不治本。为了压缩监控数据存储空间,原始 10 秒间隔的监控数据表只能归档保留 3 天时间的监控数据,但存储大小也将近有 200GB, 加上与之相关的不同时间段的数据聚合表,存储一下子突破 300GB。这还只是 Redis 监控数据的存储大小,加上其它数据存储的监控数据,至少需要 1TB+空间的 MySQL 存储。


数据集合任务管理复杂、后期监控原数据回溯缺失、MySQL 存储空间日益增长带来的隐患,都是亟待解决的问题。


二、时序数据库选型


为了解决 MySQL 监控数据存储的问题,我们把注意力转移到了适合存储监控数据的时序数据库上。市面上各种时序数据库产品琳琅满目,有老牌的,也有后起之秀,经过⼀系列调研选型,我们选择了 TDengine,主要是因为其具备的如下几大优点:

  • 采用分布式架构,可支持线性扩展
  • 数据存储压缩率超高
  • 集群模式支持多副本,无单点故障
  • 单机模式性能强悍
  • 安装部署维护简单
  • SQL⽀持时间维度聚合查询
  • 客户端支持 RESTful API


值得一提的是,TDengine 的 SQL 原生语法支持时间维度聚合查询,同时数据存储压缩率⾼存储空间小, 这两点直接切中了我们的痛点。落地后实测相同数据的存储空间只有 MySQL 存储空间的十分之⼀甚至更少。还有⼀个惊喜是,在现有监控数据存储(MySQL)顶不住的情况下,⼀台 8C16GB 的单机版 TDengine 轻松就抗下目前所有监控流量和存储压力,且运行稳定,基本没有故障。


三、改造过程


TDengine 用于存储监控数据的超级表设计原则就是简单高效,字段⼀般都比较少,每⼀种监控项类型(INT、FLOAT、NCHAR 等)的数据存储都需要单独建立⼀个超级表,超级表⼀般都有关键的 ts、type、value 字段,具体监控项由 type 字段标识,加上必要的 tag 及少量其它字段构成。


之前监控数据存储在 MySQL 的时候,每条数据记录包含了该实例⼀次监控采样的所有监控项(25+)数据。如果采用通用的监控超级表设计原则,就需要改造采样的数据结构,改造方式有两种:

  • 改造监控数据投递的数据结构
  • 改造消费程序消费逻辑重组数据结构


但消费端有时效性要求,改造难度大,生产端涉及范围大阻力也不小。经过综合考量,后我们决定采用类似 MySQL 数据存储的表结构来设计超级表,这样的改造对原来系统入侵少,改造难度系数低,改造大致过程如下:

  • TDengine,每种数据存储的监控数据单独建库存放
taos> create database redis;  
taos> create database es;  
... ... ...  

相关文章