InfluxDB存储引擎——TSM引擎

TSM存储引擎概念

TSM存储引擎主要由几个部分组成:CacheWALTSM FileCompactor

各大组件

Cache

存储位于内存。插入数据时将数据先存入Cache,待Cache中数据到达一定数量时就将数据写入TSM File中。在每次启动InfluxDB时会先遍历所有的WAL文件,重新构造Cache,这样即使出现故障,也不会导致数据丢失。

Cache中的数据并不是无限增长的,有一个maxSize参数用于控制当Cache中的数据占用多少内存后就会将数据写入TSM File中。
maxSize默认大小为25MB,每当Cache达到阈值后,会将当前的Cache进行一次快照,之后清空当前Cache中的内容,再创建一个新的WAL文件用于写入,剩下的WAL文件最后会被删除,快照中的数据会经过排序后写入一个新的TSM File中。

目前Cache设计存在一个问题。当一个快照正在被写入一个新的TSM File文件时,当前的Cache由于大量数据写入,又达到了阈值,此时前一个快照还未完全写入磁盘,InfluxDB的做法是让后续的写入操作失败,用户需要自己处理,等待恢复后继续写入数据。

WAL

WAL文件结构并不是InfluxDB或者TSM存储引擎特有的,对于常见的关系型数据库的InnoDB存储引擎也包含WAL文件结构。WAL主要是防止写入内存还未写入磁盘数据丢失备份所用。

在插入数据时,实际流程都是同时往Cache(关系型数据库是内存内)和WAL写入数据,当服务器突然关停等问题出现可以通过WAL来恢复临时插入内存的数据。通常在启动InfluxDB或者其他关系型数据库时都会先遍历一遍WAL文件来恢复内存中还未写入磁盘的文件

TSM File

主要由四个部分组成:HeaderBlocksIndexFooter。文件格式如下:

HeaderDatablockIndexesFooter
5 bytesN bytesN bytes8 bytes

Header

Magic NumberVersion
4 bytes1 byte

Magic Number(4 bytes):表示何种存储引擎TSM存储引擎代号就是0x16d116d1
Version(1byte):表示存储引擎版本号,目前TSM1,版本号为1。

Footer

Indexes offset
8 bytes

标明了Indexes部分起始位置的offset,便于定位Indexes。

Blocks & Index

数据都是以Block最小读取单元存储在文件中。
在这里插入图片描述
文件数据块都有相应的类B+树索引,而且数据块和索引结构存储在同一个文件中。

TSM File最核心的由Series Data SectionSeries Index Section两大部分组成,Series Data Section表示存储时序数据的Block,而Series Index Section存储文件级别B+树索引Block,用于在文件中快速查询时间序列数据块。

Datablock

在这里插入图片描述
Series Data Block由四部分构成:TypeLengthTimestampsValues

Type:表示Values中的数据类型,数值数据类型通常为intlongfloat以及double等。不同的数据类型对应不同的编码方式。

Length:len(Timestamps),用于读取Timestamps区域数据,解析Block。

Timestamps时间值存储在一起形成的数据集,通常来说,时间序列中时间值的间隔都是比较固定的,比如每隔一秒钟采集一次的时间值间隔都是1s,这种具有固定间隔值的时间序列压缩非常高效,TSM采用了Facebook开源的Geringei系统中对时序时间的压缩算法:delta-delta编码。

Values:指标值存储在一起形成的数据集,同一种Key对应的指标值数据类型都是相同的,由Type字段表征,相同类型的数据值可以很好的压缩,而且时序数据的特点决定了这些相邻时间序列的数据值基本都相差不大,因此也可以非常高效的压缩。需要注意的是,不同数据类型对应不同的编码算法。

Indexes

在这里插入图片描述
Series Index Block由Index Block Meta以及一系列Index Entry构成。

Index Block Meta:最核心的字段是Key,表示这个索引Block内所有IndexEntry所索引的时序数据块都是该Key对应的时序数据。

keyLength:Key的长度
Key:表示该Index Block索引的Data Block的Key
TypeData Block的Type
count:Index Entry的数量

Index Entry:表示一个索引字段,指向对应的Series Data Block。指向的Data Block由Offset唯一确定,Offset表示该Data Block在文件中的偏移量Size表示指向的Data Block大小Min TimeMax Time表示指向的Data Block中时序数据集合的最小时间以及最大时间,用户在根据时间范围查找时可以根据这两个字段进行过滤。

Compactor

Compactor组件在后台持续运行,每隔一秒会检查一次是否需要压缩合并的数据。

主要进行两种操作。
一种是Cacahe中的数据大小达到阈值后,进行快照,之后转存到一个TSM File中。
另一种是合并当前的TSM File,将多个小的TSM File合并成一个,使每一个文件尽量达到单个文件的最大大小,减少文件的数量,并且一些数据的删除也是在这个时候完成的。

读 & 写

在这里插入图片描述

读流程

首先根据Key找到对应的SeriesIndex Block,因为Key是有序的,所以可以使用二分查找来具体实现;
找到Series Index Block之后再根据查找的时间范围,使用[MinTime, MaxTime]索引定位到可能的Series Data Block列表;
将满足条件的Series Data Block加载到内存解压进一步使用二分查找算法查找即可找到。

写流程

httpd 服务解析出要插入的所有 Points,以及数据库存储策略等内容,之后调用 PointsWriter 的 WritePoints 方法插入数据;
WritePoints 函数会根据 Point 的时间戳判断出其属于哪一个 Shard,之后调用 writeToShard 函数批量将 Points 分别写入到不同的 Shard 中。

参考文献

InfluxDB TSM存储引擎之TSMFile.
influxDB系列(四)TSM引擎(存储原理).
TSM文件格式及实例解析(一).

### InfluxDB数据库类型及其内部存储机制 #### 数据库类型 InfluxDB 是一种专为处理时间序列数据设计的时间序列数据库。这类数据库优化了对带有时间戳的数据的高效读取和写入操作,特别适合于快速变化的数据集以及高频率的数据采集环境[^1]。 #### 存储引擎 InfluxDB 使用 TSM (Time-Structured Merge Tree) 作为其底层存储引擎TSM 结合了 LSM 树的优点,在保持良好的写性能的同时提高了查询效率。具体来说: - **内存中的缓存层**:最近写入的数据会先被保存在一个称为 WAL (Write-Ahead Log) 和 memory cache 中,这有助于提高系统的吞吐量并减少磁盘 I/O 操作。 - **持久化文件结构**:当缓存达到一定大小时,这些数据会被刷新到磁盘上的 TSM 文件中。每个 TSM 文件都是不可变的,并且包含了经过排序和压缩后的键值对集合。 - **紧凑过程**:为了防止过多的小型 TSM 文件累积影响性能,后台会有定期的任务来进行 compaction 合并旧有的小型 TSM 文件成更大的文件,从而进一步提升读取速度并释放额外的空间。 此外,通过采用专门针对时间序列特点而定制的索引方法——即基于时间范围分区的技术,使得即使面对海量的历史记录也能迅速定位所需时间段内的特定条目[^2]。 ```java // Java Client 示例展示如何连接至 InfluxDB 并执行基本操作 import org.influxdb.InfluxDB; import org.influxdb.dto.Point; public class InfluxDBExample { public static void main(String[] args){ // 创建客户端实例... Point point = Point.measurement("example_measurement") .time(System.currentTimeMillis(), TimeUnit.MILLISECONDS) .addField("value", Math.random()) .build(); influxDB.write(point); } } ```
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值