首度公开!OceanBase存储系统架构的演进历程及工程实践

本文涉及的产品
云数据库 RDS MySQL Serverless,0.5-2RCU 50GB
简介: OB君:作为一款100%自研的分布式数据库,OceanBase历经了近十年的发展历程。近十年来,OceanBase的存储架构经历了多次演进,以解决业务越来越复杂苛刻的存储需求。本文整理自赵裕众(花名陈群)在2019 SACC中国系统架构师大会中的演讲。

OB君:作为一款100%自研的分布式数据库,OceanBase历经了近十年的发展历程。近十年来,OceanBase的存储架构经历了多次演进,以解决业务越来越复杂苛刻的存储需求。本文整理自赵裕众(花名陈群)在2019 SACC中国系统架构师大会中的演讲。

随着用户数据量的不断增长,基于传统共享存储的纵向扩展能力渐渐变得力不从心,分布式存储成为应对用户海量数据的标配。
作为一位架构师,在设计系统的分布式存储架构时,需要关注哪些方面呢?或者我们换句话说,对于客户来说,一个理想中的分布式存储产品应该具有哪些特性呢?

1574163242390_302f75a4_38c6_4fda_bc07_0cb6f143c146

我们认为完善的分布式存储架构应该关注这五个方面:

  • 扩展性:扩展性可谓是分布式存储有别于单机存储的重要特征,分布式存储的扩展性远远好于单机存储,但是不同分布式存储系统的扩展性之间仍然有着非常大的差异。某些分布式系统在几十个节点的量级上可能运行的很好,但是节点如果再多下去,到了上百个乃至上千个的时候可能就会面临很大的问题。用户数据的增长没有止境,如果不能做到线性扩展,那么今天能够支撑业务的系统到了明天可能就会成为业务进一步发展的阻碍。
  • 高可用:在分布式系统中出现节点故障是很常见的事情,分布式系统中的节点越多,出现节点故障的频率也就会越高。在发生节点故障时是否能够保证系统仍然可用,对于很多业务来说至关重要。根据故障类型和恢复时间的不同,高可用也分有不同的级别,系统是否可以容单点故障、多点故障、单机房故障、多机房故障、单城市故障、多城市故障?系统恢复是否可以做到天级恢复、小时级恢复、分钟级恢复、秒级恢复?不同业务场景可能会对高可用有不同的要求。
  • 一致性:一致性其实是一个被滥用的概念,很多同学会将其和数据库事务特性中ACID中的C相混淆,在这里我们特指分布式系统的一致性。那么分布式系统的一致性指的是什么?如果用一句话进行概括,我们认为一致性指的是在一个分布式的读写系统中,用户是否总能读到最新写入的数据。如果总是能读到,那么这个系统就是强一致的,否则则是弱一致的。最终一致性则是弱一致的一种特例,指的是尽管不能总是读到最新的数据,但随着写入操作的终止,最终还是可以读到最新的数据。尽管很多分布式系统都宣称提供一致性,但很多时候它们只是提供弱一致或者最终一致。强一致对于一些业务特别是和交易相关的金融业务来说至关重要,如果不能保证总是读到最新的数据,那么就会有发生资损的可能。
  • 低成本:分布式存储系统可以使用更加廉价的PC服务器来代替高端的小机及大机,在成本上具有显著的优势。但低成本并不意味着低性能,事实上由于分布式系统下有着非常多的节点,同时使用这些节点的能力可以为我们带来相比大型服务器更高的性能。低成本高性能可以为我们的用户节省更多的系统成本。
  • 易用性:低成本特性通常关注于硬件成本,易用性则关系到人力成本。对于开发同学来说,易用性意味着简单易上手的使用接口,最好学习和迁移成本为零,同时功能强大,能够满足各式各样的需求;对于运维同学来说,易用性则意味着系统稳定健壮,系统监控及运维手段完善,学习及使用门槛低。

架构演进历程

架构设计服务于业务,再完美的系统架构都需要有业务进行使用才能创造价值。对于业务来说,当然希望我们的产品能够同时具备高扩展、高可用、强一致、低成本以及零门槛的易用性,但对于系统架构师和开发者来说,这五个特性之间存在相互矛盾的不少,同时在实现这些特性时也会面临巨大的复杂性,这要求我们在做系统设计及实现时需要有所权衡。

下面我们就OceanBase创立九年多以来存储架构的演进历程,来回顾每一次架构变更背后的权衡与思考。

1574163318661_6f5e5787_740a_4bac_9bef_9411ce62b88b

1)OceanBase 0.1版本(2010年)

OceanBase由阳振坤于2010年在淘宝创立,当时淘宝大多数业务都已经按照用户维度做了分库分表,一个全新的分布式存储系统似乎很难有用武之地。最终我们找到了OceanBase的第一个业务:淘宝收藏夹,也就是我们今天打开手淘看到喜欢的商品点收藏时用到的收藏夹,直到今天它仍然跑在OceanBase数据库上面。

_2019_11_25_7_08_32

当时收藏夹面临了一个分库分表难以解决的问题,它的核心业务主要包括两张表,一张是用户表,记录一个用户收藏的商品条目,数量从几条到几千条不等;另一张是商品表,记录一件商品的描述、价格等明细信息。如果一个用户增加/删除收藏,那么相应的就向用户表中插入/删除数据就可以了;同时如果一个商家需要修改商品描述,例如修改商品价格等信息,那么相应的更新商品表就可以了。

当用户打开收藏夹时,通过用户表和商品表的连接查询,就可以展现给用户最新的商品信息。最开始的时候,这两张表是在一个数据库里面,也一直运行地很好,但随着用户数据量的增长,单个数据库放不下了,一般常用的做法是将表按照用户维度进行拆分,用户表是可以这样拆,但是商品表中没有用户字段,如果按照商品条目进行拆分,那么在用户打开收藏夹时,就需要对多个不同的库进行查询并做连接,当时的数据库中间件并没有这样的能力,即使可以这么做,一次查询也会耗费非常长的时间,会极大的影响用户体验,业务遇到了很大的困难。

OceanBase接下了用户的这个难题,如果我们分析扩展性、高可用、一致性、低成本和易用性这五个特性,那么什么是业务的刚需,什么是业务可以放弃的呢?业务最强的刚需是扩展性,因为传统的单机模式已经走到了尽头;最可以放弃的其实是易用性,因为业务对写入查询的使用非常简单,提供简单的读写接口就可以满足业务需求,业务甚至不需要在表上构建索引。同时我们也注意到业务对一致性也有一定的需求,业务可以容忍一定的弱一致读,但不能容忍数据出错。这些特性决定了OceanBase从诞生的第一天起,就是一个支持在线事务处理的关系型分布式数据库。

1574163850538_289b9e74_9660_4a15_8c9b_09baf9c7f865

我们注意到收藏夹这个业务的特性,它的存量数据比较大,但是每天的增量并不大,毕竟每天新增收藏的用户并不是特别多。它更关心数据存储的扩展性,而对写入的扩展性要求并不是很高。我们将数据分为两部分:基线数据和增量数据。基线数据是静态的,分布式地存储在ChunkServer上。增量数据写在UpdateServer上,通常是存储在内存里面,通过Redo Log支持在线事务,在每天的业务低峰期,UpdateServer上的数据会与ChunkServer上的数据做合并,我们称之为“每日合并”。MergeServer是一个无状态的Server,提供数据写入的路由与数据查询的归并;RootServer负责整个集群的调度与负载均衡。这是一个类似于LSM Tree的存储架构,这也决定了今后OceanBase的存储引擎都是基于LSM Tree的。

1574172666507_5f45c4b0_732d_4762_a5ab_76ea7f347ced

我们回过头来看OceanBase0.1的架构,它实际上具有很强的一致性,因为写入是个单点,读到的数据一定是最新写入的数据,同时成本也并不高,也具有一定的扩展性,存储空间可以很容易地做扩展,很好满足了当时业务的需求。

2)OceanBase 0.2-0.3版本(2011年)

很快OceanBase 0.1版本上线了,并为收藏夹业务提供了读服务,但业务不能把所有流量都切到OceanBase上面来,因为OceanBase 0.1版本的架构有着一个很大的缺陷:它不是高可用的。任何一台服务器的宕机都会造成数据的不可访问,这对于收藏夹这样的业务是无法接受的。很快我们带来了OceanBase 0.2版本的架构,补上了高可用的短板。

1574163889950_b5230c44_9708_4f13_896c_6bd094764236

在OceanBase 0.2版本中我们引入了主备库模式,这也是当时传统数据库常用的容灾模式,数据通过redo log从主库同步到备库,当主库发生问题时,可以把备库切换为主库继续提供服务。redo log的同步是异步的,这意味着主备的切换是有损的,可能会丢失若干秒的数据。

1574172640113_15275d8e_6dd1_4533_a93a_2bf5e3df0e19

我们将OceanBase 0.2版本和OceanBase 0.1版本的架构进行对比,会发现OceanBase 0.2版本终于有了高可用这一重要特性,但高可用的获得不是没有代价的,首先系统不再是强一致的了,我们不能够保证业务总是能够读到最新的数据,在宕机场景下,数据可能会有部分丢失;其次主备库的引入极大地增加了成本,我们使用的机器数量翻番了。之后的OceanBase 0.3版本基于OceanBase 0.2版本做了很多代码上的优化,进一步降低了系统成本,但从架构上来说和OceanBase 0.2版本并没有显著的差别。

3)OceanBase 0.4版本(2012年)

随着收藏夹业务的成功,很快我们接到了更多新的业务,淘宝直通车是一个面向商家的业务,也面临着分库分表难以解决的问题。首先淘宝直通车的数据量越来越大,单库难以支撑,同时它又是一个OLAP类型的业务,有很多多表间的关联查询,每张表的维度又各不相同,无法统一按照用户id进行拆分。对于OceanBase的扩展性、高可用以及低成本业务都很满意,但是接口使用确实是太痛苦了。那么问题来了,什么是最好的接口语言?对于编程来说,可能不同的语言都有不同的拥趸,但对于数据操作来说,我们认为SQL一定是最好的语言。对于简单的KV查询,你可能会觉得SQL过于沉重了,但当你的业务慢慢复杂起来后,SQL一定是使用最简单轻便的。

1574164035170_2783fb03_a990_4ba2_95bb_e2b76ab8e2d5

在OceanBase 0.4版本,我们对SQL有了初步的支持,用户可以使用标准SQL来访问OceanBase,支持简单的增删改查以及关联查询,但对SQL的支持并不完整。同时OceanBase 0.4版本也是我们最后一个开源版本。

1574164095517_59810cfb_bee4_4785_b75b_c0c41c63e8cf

对比OceanBase 0.4版本和OceanBase 0.2版本的架构,在OceanBase 0.4版本我们最终补上了易用性的白板,开始慢慢有了一个标准分布式数据库的样子。

4)OceanBase 0.5版本(2014年)

2012年底的时候,OceanBase团队来到了支付宝。当时支付宝面临着全面去掉IOE的强烈需求,IOE的成本太高了,但PC服务器的稳定性难以和高端存储相比,如果我们使用MySQL这样的开源数据库基于PC服务器进行替代,业务就面临着可能会丢数据的潜在风险。当时基于MySQL的容灾方案仍然只是主备同步,对于支付宝交易支付这样的核心系统来说,丢失一笔订单造成的损失难以估量。业务对数据库的强一致和高可用提出了更高的要求,也使得我们搭建了OceanBase 0.5版本的新一代架构。

1574164122994_1c2d6a4e_9a62_4aef_b9eb_2d5a96367a99

在OceanBase 0.5版本中,我们引入了Paxos一致性协议,通过多数派选举来保障单点故障下的数据一致性。一般情况下,OceanBase 0.5版本的部署模式会是三副本,当有一个副本出现问题时,另外两个副本会补齐日志并重新选出一个主提供服务,我们可以做到单点故障下不丢失任何数据,同时故障恢复时间小于30s。同时为了更好地支撑业务,在OceanBase 0.5版本中,我们全面兼容了MySQL协议,支持了二级索引并有了基于规则的执行计划,用户可以用MySQL的客户端来无缝连接OceanBase,可以像使用MySQL一样来使用OceanBase。

1574164142045_c7bbbfc1_389f_4c17_a61d_8a8c4a9f00ce

对比OceanBase 0.4版本和OceanBase 0.5版本的架构,我们发现OceanBase 0.5版本基于Paxos,有了更强的高可用以及强一致,基于SQL有了更好的易用性,但代价是从两副本变成三副本,系统成本进一步增加了50%。

5)OceanBase 1.0版本(2016年)

在OceanBase 0.5版本的架构下,业务对强一致、高可用以及易用性的需求都得到了很好的支持,痛点慢慢集中在扩展性和成本上。随着用户写入量的不断增长,UpdateServer的写入单点总是会成为瓶颈,同时三副本也带来了过高的成本消耗。OceanBase 1.0版本带来了全新的架构,重点解决了扩展性和成本的痛点。

在OceanBase 1.0版本中,我们支持了多点写入,从架构上将UpdateServer、ChunkServer、MergeServer和RootServer都合并为一个OBServer,每一个OBServer都可以承担读写,整体架构更加优雅,运维部署也更加简单。一张表可以被划分为多个分区,不同分区可以散布在不同的OBServer上,用户的读写请求通过一层代理OBProxy路由到具体的OBServer上进行执行。对于每个分区都仍然通过Paxos协议做三副本高可用,当有一台OBServer出现故障时,这台OBServer上的分区会自动切到其他包含对应分区的OBServer上提供服务。

1574164174157_d6b36c17_0298_4e15_b284_4dbf8837b2f7

在成本方面,我们注意到在Paxos协议中,需要三副本同步的只是日志,日志需要写三份,但是数据并不是,和数据相比日志量总是小的。如果将日志和数据分开,我们就可以使用两副本的存储开销实现三副本高可用。在OceanBase 1.0版本中,我们将副本分为两种类型:全功能副本和日志副本,其中全功能副本既包含数据也包含日志,提供完整的用户读写;日志副本只包含日志,只进行Paxos投票。
同时在OceanBase 1.0版本中,我们引入了多租户的概念,在同一个OceanBase集群中,可以支持多个不同的租户,这些租户共享整个集群资源,OceanBase会对不同租户的CPU、内存、IO及磁盘使用进行资源隔离。租户可以根据自己的需要配置不同的资源容量,集群会根据不同OBServer的负载做动态的负载均衡。这使得我们可以把很多个小租户部署到同一个大集群中来,降低整体的系统成本。

和OceanBase 0.5版本相比,OceanBase 1.0版本的扩展性有了大幅提升,而且由于引入了日志副本和多租户技术,在成本上有了大幅降低;但扩展性的提升不是没有代价的,多点写入带来了巨大的复杂性。首先用户的写入并不一定会只写单个分区,对于多个分区的写入不可避免会带来分布式事务,我们使用两阶段提交协议来完成分布式事务。其次在一个分布式系统中获取一个全局单调递增的时间戳是极其困难的,由于没有全局时钟,我们基于局部时间戳做单分区内的读写并发控制,这使得系统的一致性有了一定的限制,虽然单分区的查询仍然是强一致的,但跨分区的查询无法保证读的强一致,这对于用户而言会是一个不小的限制。同时由于分区的关系,二级索引成为了分区内的局部索引,这要求索引键中一定需要包含分区键,无法支持全局的唯一索引,这对于用户使用也造成了一定的不便。

1574166141124_78395cb7_5419_4958_a33c_3fab4b659cbb

6)OceanBase 2.0版本(2018年)

OceanBase 2.0版本的外部整体架构与OceanBase 1.0版本没有太大差别,仍然是一个share nothing的三副本架构,但在内部我们对扩展性、高可用、一致性、低成本和易用性都做了极大的提升。

ob_

在扩展性方面,我们实现了分区分裂的功能。在建表的时候,用户对合适的分区数可能没有很好的估计,当分区过大时,可以通过分区分裂来使得分区数变多。尽管分区分裂是一个比较重的DDL操作,在OceanBase 2.0版本中,分区分裂是可以在线进行的,对用户的正常业务读写并不会造成太大影响。

1574172573915_a739ad7a_c9c3_4d54_8bee_b2d3c0127d50

在高可用方面,我们支持了主备库功能,对于某些只有双机房的用户,可以在机房内通过三副本做机房内的无损容灾,通过主备库做跨机房的有损容灾。

在一致性方面,我们支持了全局快照,真正意义上实现了分布式读写下的强一致。基于全局快照,我们也完成了对全局索引以及外键的支持。

在低成本方面,我们在事务层支持了TableGroup,允许把一组相近的表“绑定”在一起,减少分布式事务的开销。在存储层引入了数据编码,通过字典、RLE、Const、差值、列间等值、列间前缀等算法进一步压缩存储空间的占用,并且对于数据的编码是自适应的,会根据数据特征来自动选择合适的编码算法。

在易用性方面,我们支持了Oracle租户,允许用户在同一套ObServer集群中同时使用MySQL租户与Oracle租户,并且支持存储过程、窗口函数、层次查询、表达式索引、全文索引、ACS、SPM、回收站等功能。

总结

尽管今天的OceanBase 2.0版本在扩展性、高可用、一致性、低成本以及易用性方面做到了更好的平衡,但这样的架构并不是一蹴而就的,从OceanBase 0.1版本到OceanBase 2.0版本的发展历程来看,OceanBase的架构总是在一直进化,为了能够更好地服务于业务,很多事物总是面临着许多权衡取舍,一项特性的提升会以其他特性的降低为代价。架构的优化演进没有终点,未来为了更好满足业务的需求,OceanBase的架构还会不断进行演化。

作者介绍

赵裕众(花名陈群),蚂蚁金服高级技术专家,目前在OceanBase团队负责存储相关的开发工作。2010年于中国科学技术大学获得计算机博士学位,同年加入支付宝从事分布式事务框架的研发,2013年加入OceanBase团队。

OceanBase 技术交流群

— 想了解更多OceanBase背后的技术秘密?

— 想与蚂蚁金服OceanBase的技术专家深入交流?

— 只需扫码关注OceanBase微信公众号并回复“加群”,快速加入OceanBase技术交流群!
— 有钉钉的小伙伴也可以加入OceanBase钉钉互动群:搜索群号21949783

相关实践学习
基于CentOS快速搭建LAMP环境
本教程介绍如何搭建LAMP环境,其中LAMP分别代表Linux、Apache、MySQL和PHP。
全面了解阿里云能为你做什么
阿里云在全球各地部署高效节能的绿色数据中心,利用清洁计算为万物互联的新世界提供源源不断的能源动力,目前开服的区域包括中国(华北、华东、华南、香港)、新加坡、美国(美东、美西)、欧洲、中东、澳大利亚、日本。目前阿里云的产品涵盖弹性计算、数据库、存储与CDN、分析与搜索、云通信、网络、管理与监控、应用服务、互联网中间件、移动服务、视频服务等。通过本课程,来了解阿里云能够为你的业务带来哪些帮助     相关的阿里云产品:云服务器ECS 云服务器 ECS(Elastic Compute Service)是一种弹性可伸缩的计算服务,助您降低 IT 成本,提升运维效率,使您更专注于核心业务创新。产品详情: https://www.aliyun.com/product/ecs
相关文章
|
30天前
|
负载均衡 测试技术 持续交付
高效后端开发实践:构建可扩展的微服务架构
在当今快速发展的互联网时代,后端开发扮演着至关重要的角色。本文将重点探讨如何构建可扩展的微服务架构,以及在后端开发中提高效率的一些实践方法。通过合理的架构设计和技术选型,我们可以更好地应对日益复杂的业务需求,实现高效可靠的后端系统。
|
15天前
|
Kubernetes 安全 Java
构建高效微服务架构:从理论到实践
【4月更文挑战第9天】 在当今快速迭代与竞争激烈的软件市场中,微服务架构以其灵活性、可扩展性及容错性,成为众多企业转型的首选。本文将深入探讨如何从零开始构建一个高效的微服务系统,覆盖从概念理解、设计原则、技术选型到部署维护的各个阶段。通过实际案例分析与最佳实践分享,旨在为后端工程师提供一套全面的微服务构建指南,帮助读者在面对复杂系统设计时能够做出明智的决策,并提升系统的可靠性与维护效率。
|
7天前
|
消息中间件 运维 监控
现代化软件开发中的微服务架构设计与实践
本文将深入探讨现代化软件开发中微服务架构的设计原则和实践经验。通过分析微服务架构的优势、挑战以及常见的设计模式,结合实际案例,帮助开发者更好地理解如何构建可靠、可扩展、高效的微服务系统。
|
7天前
|
负载均衡 Java 开发者
细解微服务架构实践:如何使用Spring Cloud进行Java微服务治理
【4月更文挑战第17天】Spring Cloud是Java微服务治理的首选框架,整合了Eureka(服务发现)、Ribbon(客户端负载均衡)、Hystrix(熔断器)、Zuul(API网关)和Config Server(配置中心)。通过Eureka实现服务注册与发现,Ribbon提供负载均衡,Hystrix实现熔断保护,Zuul作为API网关,Config Server集中管理配置。理解并运用Spring Cloud进行微服务治理是现代Java开发者的关键技能。
|
8天前
|
敏捷开发 监控 前端开发
深入理解自动化测试框架Selenium的架构与实践
【4月更文挑战第16天】 在现代软件开发过程中,自动化测试已成为确保产品质量和加快迭代速度的关键手段。Selenium作为一种广泛使用的自动化测试工具,其开源、跨平台的特性使得它成为业界的首选之一。本文旨在剖析Selenium的核心架构,并结合实际案例探讨其在复杂Web应用测试中的高效实践方法。通过详细解读Selenium组件间的交互机制以及如何优化测试脚本,我们希望为读者提供深入理解Selenium并有效运用于日常测试工作的参考。
14 1
|
11天前
|
Linux 数据安全/隐私保护
Linux基础与服务器架构综合小实践
【4月更文挑战第9天】Linux基础与服务器架构综合小实践
1234 8
|
20天前
|
消息中间件 监控 API
构建高性能微服务架构:从理论到实践
【4月更文挑战第4天】 在当今互联网应用的快速迭代和高并发需求下,传统的单体应用架构已不足以满足市场的灵活性与扩展性要求。微服务架构以其独立部署、弹性伸缩、技术多样性等优势,成为众多企业转型升级的首选方案。本文将深入探讨如何构建一个高性能的微服务系统,涵盖关键组件的选择、系统设计的考量以及性能优化的策略,旨在为开发者和架构师提供一套实用的指导思路和具体实践步骤。
|
23天前
|
消息中间件 安全 API
构建高效微服务架构:策略与实践
【4月更文挑战第1天】在数字化转型的浪潮中,微服务架构已成为企业追求敏捷、可扩展和灵活部署的重要技术手段。本文将深入探讨如何通过合理的设计原则和先进的技术栈,构建一个高效的微服务系统。我们将剖析微服务设计的核心要点,包括服务的划分、通信机制、数据一致性以及安全性问题,并结合案例分析,展示如何在现实世界中应用这些策略以提升系统的可靠性和性能。
|
23天前
|
设计模式 API 持续交付
构建高效微服务架构:从理论到实践
在当今快速迭代和部署的软件开发环境中,微服务架构已成为一种流行的设计模式,它允许开发团队以模块化的方式构建、维护和扩展应用程序。本文将深入探讨微服务的核心概念,包括其定义、优势、挑战以及如何在实际项目中实施。我们将通过一个实际案例来展示如何将传统的单体应用拆分成一系列独立、松耦合的服务,并通过容器化、服务发现、API网关和持续集成/持续部署(CI/CD)等技术手段来管理这些服务。
|
26天前
|
存储 Java 应用服务中间件
【分布式技术专题】「架构实践于案例分析」盘点互联网应用服务中常用分布式事务(刚性事务和柔性事务)的原理和方案
【分布式技术专题】「架构实践于案例分析」盘点互联网应用服务中常用分布式事务(刚性事务和柔性事务)的原理和方案
45 0