作者介绍 :
陈现麟,伴鱼技术中台负责人,从 0 到 1 搭建伴鱼技术中台,对分布式架构、服务治理、稳定性建设、高并发高 QPS 零碎和中台化的组织架构搭建有肯定的教训,崇尚简略优雅的设计,关注云原生和分布式数据库。
PingCAP 团队的论文《TiDB: A Raft-based HTAP Database》入选 VLDB 2020,这是对 TiDB 数据库阶段性成绩的必定,十分为国内数据库技术的疾速倒退而感到高兴。因为对于 TiDB 数据库在高可用、程度扩大和 ACID 事务的实现计划很久以前就曾经公布出来了,对于这些主题大家都比拟相熟,所以就不再赘述了,上面次要谈谈论文中对于如何实现数据强一致性且资源隔离的 HTAP 数据库的一些启发和感想。
OLTP or OLAP
大家都晓得数据库分为 OLTP 和 OLAP 类型,那么数据库为什么要分成这两类型呢?
首先,OLTP 和 OLAP 是定义数据处理形式的,这是两个差别特地显著的工作负载,OLTP 操作是波及数据少,然而实时性和事务要求高,并发量大;OLAP 操作是实时性和事务要求低,然而波及数据量大,并且查问模式不固定,很难通过索引来笼罩。其次,晚期的数据库是没有 OLTP 和 OLAP 类型之分的,在一个数据库(次要为关系数据库)里进行 OLTP 和 OLAP 类型的数据相干的操作,起初数据量缓缓变大,间接在关系数据库中同时解决 OLTP 和 OLAP 类型的申请开始力不从心,更坏的状况可能还会影响到 OLTP 类型的申请,所以针对 OLAP 场景设计了更合乎其工作负载的 OLAP 类型数据库,通过将 OLTP 类型的数据同步到 OLAP 类型的数据库,而后再进行 OLAP 类型的操作。
通过下面的形式,解决了 OLTP 和 OLAP 类型工作负载抵触的问题,然而引入了一次额定的内部数据复制(从 OLTP 到 OLAP),因此也导致了 OLAP 类型操作数据的实时性和一致性失落的问题。这是从数据库系统内部通过异构零碎来解决这一个问题,就义了数据的实时性和一致性,在论文中,TiDB 提出了一个新的计划,从数据库系统外部来解决这个问题,同时防止数据的实时性和一致性的失落。
数据强一致性 or 资源隔离
前文中,咱们谈到 OLTP 和 OLAP 是两种差别十分大的工作负载,通常要两者兼得的计划分为:
- 设计一套同时适宜 OLTP 和 OLAP 工作负载的存储引擎,在这一个存储引擎来解决所有的数据申请,这样数据的实时性和一致性的问题很好解决,然而 OLTP 和 OLAP 工作负载互相不影响是一个很难解决的问题,并且一套存储引擎要同时适宜 OLTP 和 OLAP 工作负载,在存储引擎的设计与优化上的限度是比拟多的,感觉这是在设计一种五彩斑斓的黑。
- 在数据库外部同时存在两套存储引擎,散布负责 OLTP 和 OLAP 工作负载,这能够很好防止下面的问题,然而数据须要从两套存储引擎中复制,这样会导致同时满足数据强一致性和资源互相隔离是一个很难解决的问题。
论文中,TiDB 抉择的是计划 2,针对 OLTP 工作负载提供一个行存引擎 TiKV,针对 OLAP 工作负载负载提供一个列存引擎 TiFlash,那么数据强一致性和资源互相隔离怎么解决呢?
一般来说,对于一个分布式存储系统,数据强一致性和资源互相隔离常常是一个二选一的选择题,抉择数据强一致性,个别是通过同步复制的形式(比方同步双写等)将数据复制到多个相干的实例上,那么将导致所有的计算与存储资源都会紧耦合在一个零碎中,一个部分的小问题可能会导致其余的局部受到影响,牵一发而动全身;而抉择资源互相隔离,个别是通过异步复制的形式(比方主从同步等)将数据复制到其余的相干实例上来实现的,这样能够确保资源的互相隔离,然而数据强一致性得不到保障。
对于这个问题,TiDB 论文给出的解决方案是:扩大 Raft 算法,减少 Learner 角色。
Follower or Learner
TiKV 将每一段间断的数据称为一个 Region(默认 96 M),每一个 Region 是一个 Raft Group,通过 Raft 协定从 Leader 节点向 Follower 节点复制数据,这是一个同步复制的过程(超过半数节点复制实现就算胜利复制),如果 TiFlash 也采纳 Follower 的形式来同步数据,那么 TiKV 和 TiFlash 之间的数据复制能够简略了解为同步复制(其实严格来说算是介于同步和异步之间的复制,因为如果 TiFlash 的 Follower 同步慢或者挂掉后,相当于减少了一个复制失败的节点,这样就升高了多数派节点复制胜利的概率,也就升高了 TiKV 的可用性)的,这样两个存储引擎之间就会相互影响,无奈达到资源隔离的指标。
因而,TiDB 扩大了 Raft 算法,减少 Learner 角色。Learner 角色只异步接管 Raft Group 的 Raft 日志,它不参加 Raft 协定来提交日志或选举领导人,这样,在数据的复制过程中,TiFlash 的 Learner 节点对 TiKV 的性能开销十分小。TiFlash 通过 Learner 角色承受到数据后,将行格局元组转换为列式数据存储,达到了数据在 TiDB 集群中同时行存储和列存储的目标。
到这里,大家可能会发现一个问题,TiFlash 的 Learner 角色是异步承受 Raft Group 的 Raft Log,那么怎么保障 TiFlash 的数据强一致性呢?
这个问题是在 TiFlash 读数据的时候来解决的。相似 Raft 的 Follower Read 的机制,Learner 节点提供快照隔离级别,咱们能够通过特定工夫戳从 TiFlash 读取数据。在接管到读取申请后,Learner 向其 Leader 发送一个 readindex 申请,Learner 依据收到的 readindex 阻塞期待相应的 Raft Log 同步胜利并且回放到本地存储后,再依据申请的工夫戳过滤出满足要求的数据。
这样,TiDB 就将同步的数据复制机制转变成异步的数据复制机制了,并且保障了数据的强一致性。在 TiFlash 读数据的时候,TiFlash 的 Learner 只须要和 TiKV Leader 节点做一次 readindex 操作,这是一个十分轻量的操作,所以 TiKV 和 TiFlash 之间的影响会十分小。论文中试验的数据也验证了这一点,TiDB 中,同时进行 AP 和 TP 操作,AP 操作对 TP 吞吐量的影响最多不到 10%,TP 操作对 AP 吞吐量的影响最多不到 5%。
另外,论文的试验表明中,TiDB 在从 TiKV 到 TiFlash 异步数据复制机制导致的数据提早也十分小:在 10 个 warehouses 的数据量下,数据复制的提早大部分在 100 ms 以下,最大不超过 300 ms;在 100 个 warehouses 的数据量下,数据复制的提早大部分在 500 ms 以下,最高不超过 1500 ms。并且这个数据的提早不会影响 TiFlash 的一致性级别,只会让 TiFlash 上的申请略微慢一点,因为承受到读申请的时候须要去做一次数据同步。
HTAP or(OLTP and OLAP)
到这里,TiDB 有了两个存储引擎:对 OLTP 敌对的行存 TiKV,对 OLAP 敌对的列存 TiFlash,其实这个不要害,要害的是这个两个存储引擎的数据同步是强一致性的,能对外提供统一的快照隔离级别,这对于计算层的查问优化器来说是一个十分大的劣势,对于一个申请,查问优化器能够有三种扫描形式抉择:TiKV 的行扫描和索引扫描,TiFlash 的列扫描,并且对于同一个申请,能够针对不同的局部采纳不同的扫描形式,这为查问优化器提供了微小的优化空间。从论文的试验数据也表明,同时应用 TiKV 和 TiFlash 的 AP 申请比独自只应用任何一个都是更优。
咱们再回到文章的结尾,当初因为数据库因为须要好解决 OLTP 和 OLAP 工作负载,将数据库按工作负载分为 OLTP 和 OLAP 类型数据库,而后让使用者再将申请分类成 OLTP 和 OLAP 类型申请相应类型的数据库,在这里却是另一种解决形式:对于使用者来说只有一个数据库,数据库通过对申请进行剖析后决定用哪一个或者同时应用两个存储引擎,将数据库和查问按工作负载进行分类的形式打消,这个一个更高层次的形象。
人们碰到一个问题,在以后找不到基本的解决方案时,总是先将问题按场景解构,在每一个小场景中一一解决而达到解决问题的目标,这只是一个权宜之计,期待实践或者技术提高后,再从根本上解决问题。比方在通信技术的倒退过程中,先用有线电话解决在固定地点通信的问题,而后用寻呼机挪动承受信息,再加有线电话来解决挪动通信的问题,最初手机的呈现,间接解决了远距离通信的问题,在这之前通过解构通信场景针对性的解决方案有线电话和寻呼机就缓缓退出历史舞台了。对于数据库来说也是一样,先分成不同的工作负载一一解决,最初必定会造成对立来计划来解决的,TiDB 向前走了一大步,咱们刮目相待。
单点 or 程度扩大
论文中也发现了一个比拟有意思的中央,因为在分布式架构中,任何不能程度扩大的单点问题都是原罪,因为只有有一个不能程度扩大的单点,实践上就有可能成为整个零碎的瓶颈,TiDB 作为一个可程度扩大的分布式数据库,在架构上是有一个单点依赖的:从 PD 取得工夫戳。在论文中,通过严格的性能测试证实这个中央不会成为整个零碎的瓶颈,感触到 TiDB 满满的求生欲了。
齐全的去中心化 or 对立的中心化调度
目前的分布式存储系统,国外呈现了很多齐全的去中心化架构设计,比方 Cassandra 和 CockroachDB,然而 TiDB 的架构设计不是齐全去中心化的,它有一个核心大脑角色 PD,正好和东西方的意识形态对应上了,小政府与大政府的计划,这也是一个比拟有意思的中央。
Vitalik Buterin 指出抉择齐全去中心化设计的次要起因:fault tolerance、attack resistance、collusion resistance。因为数据库都是部署在外部可信赖的网络,所以 attack resistance、collusion resistance 都不会是问题,这和比特币等数字货币为了确保不能被某一些人或者组织管制,出于社会和政治方面的起因采纳去中心化架构是不一样的,并且 fault tolerance 在中心化的架构也是能够解决的。
另外,更重要的是对于 TiDB 等 NewSQL 或者 HTAP 数据库自身就是为海量数据设计的,数据库集群治理的节点和数据量会越来越大,特地是与云原始的弹性能力联合后,数据库的智能调度能力将是决定数据库性能和稳定性的关键因素,然而去中心化的架构会让调度决策变得艰难,特地是须要全局视角和多节点协同的调度决策会更加艰难。
所以,只有中心化角色不是零碎瓶颈,那么中心化的调度是有其人造的劣势的,毕竟对于调度来说,最重要的是全局视角和多节点协调能力。TiDB 对于其中心化的大脑角色 PD 定位是十分轻量,没有长久化调度相干状态的信息,所以不会是影响整个零碎的程度扩大能力。
当初 or 将来
从 TiDB 的外部来看,咱们能够看到 TiDB 是彻底的存储计算拆散架构,目前计算层有两个引擎:SQL Engine 和 TiSpark,存储层也有两个引擎:TiKV 和 TiFlash,将来,不论是计算层还是存储层都能很不便的扩大到新的生态中,所以 TiDB 的指标感觉不仅仅只是一个数据库,同时也是在打造一个分布式存储的生态。
从单集群 TiDB 的角度来看,数据强一致性但资源互相隔离的 HTAP 是一个十分高效的能力,省去了数据从 OLTP 数据库同步到 OLAP 数据库的过程,也省去了将 OLAP 数据库计算结果须要提供在线业务应用时,再将数据同步到 OLTP 数据库的过程,这样,工程师都开开心心的搬砖和写 SQL,而不是频繁的搬数据。比起搬砖来说,搬数据像运水,更容易呈现洒水、渗水等问题。
从多集群 TiDB 的角度来看,尽管 TiDB 提供了 HTAP 数据库程度扩容的能力,然而没有提供租户隔离能力,导致出于业务隔离、数据级别隔离和运维保障(比方备份和复原)等方面的起因,所以从目前来看,不可能将整个公司的所有数据都放入一个 TiDB 集群中,那么尽管 TiDB 提供了 OLAP 能力,然而如果须要做 AP 操作的数据分布在多个集群中,这样仍然须要将多个集群的数据从内部同步到一个提供 OLAP 能力的数据库中(能够是 TiDB),导致后面 TiDB 通过 HTAP 解决的问题又再一次呈现。感觉一个可行的思路是在 TiDB 集群之上减少一个相似 Google F1 层,这样在一个对立的 F1 层下,能够有很多个 TiDB 集群,每个 TiDB 集群之间是彻底隔离的,每一个 TiDB 集群相当于一个租户,F1 层提供元数据的治理、读写申请的路由能力和跨 TiDB 集群的 AP 能力;另一个思路是在 TiDB 外部来解决,在存储层减少租户的概念,每个租户对应一组存储节点,这样租户之间存储层是隔离的,计算层能够做跨租户的 AP 操作。总的来说,这是一个存储层心愿资源隔离,然而计算层心愿对立视角的问题,期待 TiDB 后续的解决方案。
最初
最初,咱们聊聊这篇论文的价值,一般来说工程论文的价值和学术论文是不一样的,工程论文的奉献,很多时候不是思维、实践等方面有特地大的翻新,而是通知大家,这个方向是能够行的,通过确定性的工程实现来缩小了很多不确定的摸索。比方 Google 的 GFS、MapReduce、Bigtable 相干的论文,在学术上翻新是不大的,简直所有的思维和实践都是曾经存在的,然而它通知大家,将其分布式实现是可行的,这个意义就十分大了,极大地推动了分布式存储系统的遍及与倒退。
所以,TiDB 的论文作为业界第一篇 Real-time HTAP 分布式数据库工业实现的论文,心愿能减速 Real-time HTAP 分布式数据库的遍及与倒退,从这个层面来说,这个意义是十分大的。