DockOne微信分享(一六八):DBaaS在金融生产环境的落地实践


【编者的话】本次技术分享内容主要包含DBaaS平台概念的解释,DBaaS平台在客户生产环境落地的探索历程。在金融行业客户生产环境落地DBaaS时遇到的困难和解决的方法。在管理有状态服务时有哪些特殊的管理特性,以及在金融客户生产环境中真实的案例分析和经验分享。

在开始前,我想先介绍介绍一下我们在数据库即服务(DBaaS)方向的努力过程。
1.png

我们是在2013年,当时云计算概念刚开始推广,中国银联研究院需要完成一个数据库云的研究性项目。在当时很多云计算项目都是基于虚拟化,但是我们认为虚拟化不是未来,又由于我们对操作系统比较熟悉,所以基于CGroup的资源隔离技术开发出第一套DBaaS原型。

到了2014年,Docker容器技术已经在社区很火。眼前一亮,觉得这就是我们需要的容器封装技术,于是我们决定在公司内部基于Docker重构。

2015年之前,我们用Docker技术解决容器封装和使用,但是又有一个新问题摆在我们面前,那就是资源调度和编排问题。当时容器编排的概念刚刚开始,在看到Swarm或Kubernetes之前,我们一直在自己开发管理和调度逻辑,碰到各种需求变化带来的问题。经过调研我们最终选择了Swarm。在2015年基于Docker的背景下,我们认为这也是唯一的选择。

经过两年的改造和进化,DBaaS也从原型变成一个相对可用的数据库云平台。在2016年中国银联信息总中心邀请我们一起参与开发“生产级环境可用的DBaaS平台“。这对于我们来说又是一个新挑战,因为当时把数据库这样的有状态服务放入容器中,进行服务化的管理,难度巨大,也没有其他借鉴的案例。虽然经过前两年的积累和研发,在容器编排和数据库服务化管理这两个方面我们已经积累了经验,但要运行在中国银联的生产环境,最大挑战还是来自于底层技术,存储方案、网络方案和高可用调度方案,这三个方面才是决定能否在生产环境中稳定运行的三个关键指标。又经过一年的努力我们自己找到了相对应的方案并验证可行。成功完成了中国银联第一期生产区DBaaS项目。

2017年,我们在基于一期项目的基础上,增加了支持更多类型数据的服务,不仅支持MySQL,还添加了Redis支持,定义了更灵活的服务编排模型以适应将来更多不同类型数据服务。在金融行业客户生产环境推广后,由于新的互联网模式业务,对后端基础服务的需求会快速增长,并且需求的数据类型也更多,不仅限于数据库,应该说可以是所有的数据类型的服务。

花了点时间和大家分享了我们一路走来,从一个研究性项目,到公司开发的产品,到在金融客户生产环境可用的平台的整个过程。

其实在整个过程中,我们也在不断摸索前进,从开始寻找资源隔离技术,到寻找资源管理,到服务编排模型,再到寻找多类型数据服务支持。整个过程是一个从下到上渐进的过程。

在2013年我们项目团队对DBaaS理解:只是一个数据库服务管理,只是负责最基本的的数据库服务部署“交付、启动、停止“这样最日常的操作。到2015年,我们在重构DBaaS过程中认识到它其实应该是“数据库资源池管理平台”。2016年后我们进一步认识到DBaaS是“整合资源和服务结构,以服务化的方式提供数据服务的平台“。

从DBaaS平台理解变化可以看出我们由下到上演进的过程,实现了从软件到平台的不同阶段,资源池化及自动化,服务化。

在每个阶段都我们都会碰到一些核心问题:

1. 服务化的最小管理单位是什么

这个问题的答案,拿到今天来看也许根本不是问题,因为在容器编排工具选择上大家一致都会选择Kubernetes。在Kubernetes中已经定义的了Pod概念。
2.png

在这里我就不赘述了,但是我们是在2013年开始开发DBaaS项目的,当时我们能够借鉴对象是虚拟机。
[attach]13491[attach]
当时我们设计的最小资源管理对象:unit。

unit我们定义是一个服务中的最小管理对象,它是由一个容器(包含Namespace,二进制版本,环境变量),多个逻辑卷对象和目录对象,一个网卡设备和IP,和配置文件对象。

我们就是把一个程序需要的部分都拆分管理,当时我们内部讨论时发现,这个设计和容器设计思想似乎背道而驰,但是放在有状态服务管理的维度去看问题时,也许这个是比较好的解决方案。

在我们设计unit时,最主要思想还是分而治之,把资源进行计算,存储,网络分离之后,我们就可以对不同类型的资源进行管理,并且满足有状态服务在日常运维,在线扩容,在线变更的这些基本的核心需求。

2. 服务模型如何定义

作为DBaaS平台,其实就是对数据库服务的管理,合理灵活的服务模型才能适配更多不同类型的服务。

通过定义最小的管理对象unit,我们定义了最小的资源模型。但是对于一个完整的数据库服务是完全不够的。因为在数据库架构中为了满足分布式的一些特性,数据库软件大都会有复制的集群结构,并且不同结构由于特性不同而导致了管理操作的不同。所以针对于完整的数据库服务,需要对unit管理对象进行组合叠加后才是一个完整的服务对象,才能实现服务化。
4.png

这是我们对服务的定义,主要有三个对象组合叠加而成,单元、子服务、服务。

一个子服务是由多个单元组成,子服务会管理其拥有单元的关系,比如一组具备主从复制关系的MySQL,一组具备sharding关系的Redis等可以根据需求进行定义。

一个服务是由多个子服务组成,服务会管理其拥有子服务的叠加关系,比如一组ProxySQL和MySQL的关系,一组ProxySQL和多个MySQL的关系等。同样也可以根据需求进行定义,这样我们通过横向和纵向的两个对象,把分散的unit对象组合在一起。

从服务资源模型看,通过设计子服务对象固化一类unit的组织关系,可以使用配置文件的管理方式实现,也可以使用执行命令脚本的方式实现。通过设计服务对象,叠加多个子服务对象丰富服务的组织结构,为服务化管理提供有效的管理对象。

在整个服务的管理中,有状态服务相比于无状态服务有一个很明显的区别,有状态服务需要固化和资源的关系,固化一组服务中不同组件unit的关系。并且在发生变化时,不能通过摧毁和重建的方式进行改造,必须在原有状态下,进行增量变化的方式进行变化。

简单来说,无状态服务是通过重启模式变化的,有状态服务时通过继承方式变化的。

所以管理有状态服务需要更加复杂对象来进行记录和延续。

3. 如何定义资源模型

定义资源模型,这个过程其实和Kubernetes中CRD过程很像,主要我们对于定义资源模型主要诉求来源于映射真实的硬件对象,进行逻辑管理,并且通过对硬件使用标签方式,来完成在分配资源到多个硬件对象上,来感知硬件高可用属性。
5.png

在图中有八个资源对象,分别是:site站点、region区域、Cluster集群、Node主机、Data storage外置存储、IP address地址池、images容器镜像、backup storage备份存储。

从这些对象都可以找到相应的证实物理对象。这些对象的产生,一个原因是由于在规模化管理硬件时,需要这样的逻辑对象来管理,更重要的原因是,针对于数据库,需要多个硬件设备来保证其高可用。

比如我们在产生一个服务时,如果指定高可用属性,那么分配算法就会过滤这些资源标签,并且根据高可用原则进行过滤,从机房、机架电源、网络交换机、物理机、外置存储的角度进行多方法的高可用筛选。保证服务在地理位置、电源、网络、主机、存储都具备高可用,并且体现在整个服务的部署结构中。

很高兴,今天和大家分享我们在建设DBaaS平台的经验和思考。今天时间有限,主要还是在分享设计时一些经验和想法。下次有机会可以和大家分享,一些具体技术细节,比如分配算法,分配模型,网络架构的实现和存储架构的实现。

Q&A

Q:请问是采取什么策略升级这些数据库类型的服务?升级过程有宕机时间吗?如果没有,会有双写问题吗?

A:在设计中是升级操作就是更新容器镜像。更新策略会根据数据库的高可用结构进行摇摆升级。
Q:具体是实现方式是怎样,有没有用到StatefulSet,或者StatefulSet的区别?

A:没有用到StatefulSet,目前我们构建了一个名为服务对象,来管理服务的。应该说我们服务对象比service更复杂,可以理解为是由多个不同类型的Pod组成的。
Q:请问一下你们的binlog多长时间过期,有用什么持久化的方式存储吗?

A:我们在封装容器镜像时,针对不同服务镜像有外围的配套脚本。类似于Kubernetes中sidecat的实现。然后通过定期调用方式备份binlog到备份存储。并且清理备份过的binlog。
Q:还有关于中间件和高可用的选择,我们用MaxScale和MHA,但是并不是非常稳定?

A:的确,我们在设计DBaaS也考虑到了,由于目前在MySQL中间件和高可用套件没有一个很好的开源产品,所以很难说你必须用哪个方案实现。所以我们在开发中就将这样的需求设计为灵活的服务架构定义,我们平台支持不同类型MySQL高可用方案和中间件方案。我们在中国银联是自己开发的高可用中间件方案,通过高可用组件发现故障进行隔离,使用Proxy组件进行数据路由,使用MySQL做数据复制。在我们设计中,可定制不同服务架构来进行服务的管理。
Q:请问在这套平台里面支持比如说,前端可以让用户选择数据库运行的方式(单机)(还是读写分离、主从架构),这个是自动化配置的吗?这个过程是提前构建的容器镜像对吗?

A:数据库容器镜像是相同的,单机、主从、读写分离等不同服务架构会生成相应的配置文件和启动项,管理逻辑。整体管理会使用定义服务架构配置信息进行自动解析产生相对应的管理操作。
Q:单元、子服务、服务的理解还是比较抽象,有更易理解的例子吗?

A:单元相当于一个我们自己构建的Pod,但不同于Pod。单元只会包换一个容器。子服务内是多个相同类型的单元,这样单元就可以部署在不同物理机上,并且完成数据库的复制关系。服务是多个类型的子服务的集合,服务内的子服务会有关联关系,比如一个完整的Redis可以有一组三个sentinel组成的子服务 + 一组多Redis Proxy的子服务 + 多组主从复制的Reids。同样的类型甚至可以映射到TiDB上,可以有一组三个TiDB + 一组三个PD + 一组五个TiKV。
Q:如何理解数据库应用拆分和容器背道而驰?

A:在容器开始阶段,大家会有共同的认识就是容器只适合运行无状态服务。直到大家对容器需求越来越多,有了Petset,有了StatefulSet,甚至有了MySQL Operater。但回归到容器本质还是为统一运维标准,快速灵活的管理资源。但是有状态服务天生就是重的,需要使用继承式的方式进行管理。但为了将有状态服务放到容器,享受容器的优势,就必须进行计算、存储、网络这些关键资源的分离。
Q:请问你们的平台是用什么语言写的,有用到链路跟踪吗?

A:我们平台全部组件都是用Golang写的。目前链路跟踪还没有,我们主要是通过我们的自研的监控平台,获取监控数据,监控物理机,容器,和容器内服务的信息,进行高可用的管理,也正在和人工智能公司合作,对运维数据进行分析,进行故障智能分析。
以上内容根据2018年4月17日晚微信群分享内容整理。 分享人鲍琳,富麦科技产品架构师,中国银联DBaaS项目架构师。 DockOne每周都会组织定向的技术分享,欢迎感兴趣的同学加微信:liyingjiesa,进群参与,您有想听的话题或者想分享的话题都可以给我们留言。
3.png

0 个评论

要回复文章请先登录注册