Part 1 摘要
MatrixOne 是一款云原生数据库,不仅反对超大规模数据集上的高性能剖析查问,同时具备高吞吐, 低提早的事务读写能力。本文介绍了 MatrixOne 数据库的存储引擎 TAE(Transctional Analytical Engine)的架构。前文介绍了单机 TAE 的相干设计,本文将重点介绍云原生和存算拆散相干的几个要害组件。
点击查看前文对于 TAE(Transactional Analytical Engine)的那些事
↑↑↑点击查看前文
很多数据库在应用对象存储时,要么作为冷备应用,要么以就义提早为代价在提交事务时同步写入到对象存储中。TAE 无效的利用云存储资源,将新写入的数据先保留到日志服务的本地磁盘中,随后异步的将日志中的数据转存至对象存储中。这样 TAE 既保留了存算拆散的可能性,又防止了过高的写入提早。
比如说:
- TAE 能够治理远大于本地存储容量的数据。本地内存和磁盘都能够作为缓存,只保留最新被拜访到的数据;
- TAE 能够以很小的代价,在一个新结点上装载出残缺的数据正本。这对于服务的 HA 还有计算资源的隔离十分的重要。
-
Part 2 LogService
为了缩小写入提早,TAE 先将最新的数据长久化到日志中,随后异步的转存到对象存储里。所以 TAE 是通过协同日志和对象存储,以保障提交事务的持久性。TAE 形象出了日志层,能够以很小的代价接入任何日志服务。默认接入的是咱们自研的 LogService 日志服务。
日志服务的外围需要有以下几点: - 高吞吐
- 低提早
- 高牢靠
-
高可用
日志中存储的是最新提交事务的数据,当这些数据被异步转存到对象存储后,相干日志也会被删除。能够把日志看成一个在时间轴上的滑动窗口,TAE 推动这个窗口一直的往前滑动,窗口以外的数据会被革除,并且 TAE 会确保落在窗口内的数据量不会十分大。因而没有必要为日志服务配置大容量的磁盘。Part 3 DN(Data Node)
在写流程中,TAE 会将提交事务写入日志,并且异步的转存至对象存储。这些都产生在 DN(Data Node)结点。
上图展现了 DN 在执行一些写操作后的状态——上 面的是内存状态机,两头的是日志,最上面的是对象存储:
- 第一个事务增加元数据 Block-1, 并且插入 A、B 两行至 Block-1。事务提交的日志是 LSN=1;
- 第二个事务插入一行 C 至 Block-1。事务提交日志是 LSN=2;
-
第三个事务将 Block- 1 长久化至对象存储上,批改 Block- 1 元数据增加 location=“1”, 产生该 Block 的第二个版本。事务提交日志是 LSN=3。
DN 状态机致力于将日志里的数据转存到对象存储上,然而转存程序不齐全依赖事务日志的枯燥性,如下图:LSN[11-17]的曾经转存,然而 LSN[3-4,7-10]还在内存状态机内(起因已在单机 TAE 的文章中解释)。这只是一个长期状态,DN 会依据特定的策略推动日志的窗口一直向前挪动。
DN 会在适当的机会抉择一个事务作为快照候选点,并期待这个候选点之前的所有事务被转存后,以这个候选点的工夫戳作为快照的工夫戳保留成快照。当快照生成后,该事务之前所有的日志都能够被清理:
这里咱们将快照后所有的日志称为 LogTail。比方上图中“ckp-1”没有生成前,LSN[1-17]都是 LogTail。DN 呈现故障后,只须要从对象存储上读取最新的快照,并且从日志服务中读取 LogTail,便可复原出残缺的状态机。
Part 4 CN(Compute Node)
分布式 TAE 不仅包含 DN, 也包含负责协调所有查问负载的 CN(Compute Node)。当集群退出一个新的 CN, 它会从 DN 获取快照和 LogTail 信息,并且保护一个内存状态机。数据文件会按需从对象存储中拉取,并依据须要保留在缓存中。这种设计不须要在查问之前就拉取大量的数据文件,满足了高弹性 CN 的需要。
举例说明
退出一个 CN 到集群,此时 DN 的状态能够依照事务工夫戳形容为[1,150],示意领有从工夫戳 1 到 150 之间所有事务的数据。
DN 的状态由以下三局部组成: - 快照 [0,100],该快照蕴含 6 个数据块 [“block-1”,“block-2”,“block-3”,“block-4”,“block-5”,“block-6”]
- 长久化的数据块“block-7“[115, 140]
- 内存数据块“block-8”[120, 150]
此时新退出的 CN 状态可形容为 [0, 0]CN 接管到查问申请,假如该申请的工夫戳为 118:
- CN 查看以后状态机的状态为[0, 0], 最大工夫戳小于 118;
- CN 会向 DN 收回一条读申请,申请 0 到 118 之间的 LogTail;
- CN 收到 DN 的响应,将 LogTail 利用到本地的状态机;
- 更新 CN 状态机的状态为 [1, 118];
- 开始查问。
CN 承受到工夫戳为 130 的查问申请:
- CN 查看以后状态机的状态为[1, 118], 最大工夫戳小于 130;
- CN 会向 DN 收回一条读申请,申请 118 到 130 之间的 LogTail;
- CN 收到 DN 的响应,将 LogTail 利用到本地的状态机;
- 更新 CN 状态机的状态为[1, 130];
-
开始查问。
Part 5 协同工作
MatrixOne 反对 CN 的动静扩容以及多个 DN(动静扩容临时没有反对)。
定义表构造时,能够指定分区键,将表数据分布在多个 DN 上。每个 CN 表数据蕴含了多个 DN 分区的数据,这有利于一些跨分区的查问。纵观 DN 的职责,次要有以下三点:
1. 提交事务
a. 冲突检测
b. 写日志
c. 利用事务到状态机
2. 为 CN 提供 LogTail 服务
3. 转存最新的事务数据至对象存储中,并且推动日志窗口
用户的计算负载不会被调度到 DN, 咱们认为以后架构下 DN 的数量能够管制在无限个数量,甚至单个 DN 就能够满足大多数的需要。通过扩容 CN 的数量,进步零碎的性能。Part 6 冲突检测
事务被提交到 DN 前,会在 CN 的工作区内做一次基于事务起始工夫戳的冲突检测,在被提交到 DN 后,只会与事务起始工夫戳到以后最新工夫戳内产生的增量数据做检测。
举例说明 - CN 处理事务 Txn-[t1]的写申请时,会做一次基于工夫戳 t1 的冲突检测
-
CN 将 Txn-[t1]提交给 DN, DN 会用 Txn-[t1]的 writeset 和 [t1,now] 产生的 writeset 做一次冲突检测
增量冲突检测机制,能够进步 DN 处理事务的吞吐能力,不会随着表数据的增长而逐步降落Part 7 大事务
大事务通常会占用大量的内存,并且很可能导致冲突检测不够高效。提交大事务和同步大事务的 LogTail 也容易使 DN 成为瓶颈。
这里通过三种形式反对大事务: - CN 在提交事务前,将事务的数据建好相干索引,并写入到对象存储中,提交至 DN 的只有相干元数据;
- DN 在提交事务时,利用相干的索引减速检测;
- DN 在提交事务时,只更新元数据。
以后 MatrixOne 曾经公布 0.6 版本,也是新架构下的第一个版本,还有很多有余。咱们会在之后 0.7 和 0.8 的版本重点攻克性能和稳定性相干的问题。本文没有深入探讨一些技术细节,后续将会一一分享