如何设计和实现高可用的MySQL

欢迎你们前往腾讯云+社区,获取更多腾讯海量技术实践干货哦~mysql

本文由腾讯云数据库 TencentDB发表于云+社区专栏sql

王甲坤,腾讯高级工程师、腾讯云关系型数据库MySQL负责人,拥有多年客户端、数据库研发经验。在IOS客户端、MySQLPostgreSQLSQL Server等产品有丰富的研发和产品策划经验。数据库

img

下面开始咱们今天的主要内容,今天主要是经过什么、为何、怎么作,这条思路跟你们呈现MySQL的高可用。缓存

首先介绍一下什么是高可用?在我看来就是业务在高质量的状况下,对用户提供服务的可运行的总时长。其实咱们从事MySQL相关的工做,你们对9这个数字比较敏感,你们选择云厂商云产品的时候,首先会看它的数据库有几个9。目前腾讯云MySQL能够作到99.95,整年在25分钟的样子。服务器

据我了解,高可用最高是能作到3个9,1个6,作到4个9很困难,作到5个9就是极限了。网络

img

为何咱们要作高可用?由于咱们不可控的因素太多了,好比说,挖挖机,我记得基本上每隔一年都会出现这种相似的事件,让我记忆犹新的是2015年杭州萧山的某个主干网被刮断,致使阿里的部分服务不可用。另外,还有相似的一些停电,或者一些天灾等等。值得一提是,运维人员的一些操做失误案例,rm整个目录或者drop表,民间有说法叫从删库到跑路。不可控制的因素不少,你的数据、用户是你的,若是不可控的话,你的业务上不去。多线程

img

通常来讲,有两个指标会被看成衡量的标准,第一是RPO,第二是RTO。RPO从故障开始到业务恢复所丢失的数据量,RTO就是从故障开始到业务恢复所耗费的时长,二者都是越短越好。架构

咱们怎么作呢?通常来讲业界有三种方式,左边是基于单机存储方式,这种方式在游戏场景比较多,你们上层是用单独的计算机节点,下层用三副本保证数据的可靠性。在计算节点发生故障之后能够快速迁移到另外一个计算节点,固然咱们腾讯云的MySQL已经推出了这种模式,相对来讲很是廉价,是基础版,你们在官网均可以购买到这种模式。第二种是基于共享存储方式,也叫share disk模式,这种比较典型的是oracle的RAC架构。底层基于共享存储的方式,上层采用多个计算节点,某个计算节点故障可当即从ip列表中提出,不影响用户访问。第三种就是基于数据复制模式,也就share nothing模式,经过数据传输、复制协议达到两台主机数据一致性,也是本次讲解的重点。另外,除了存储节点的高可用,其整个链路也须要高可用,好比,我们的IDC机房,交换机,以及主机服务器等。并发

img

下面咱们介绍下基础设施的高可用。你们常常听到几个术语,第一是同城双活,第二是两地三中心,两地三中心对于金融相关的场景是个强需求,其实说白了就是说咱们在同城两个节点相差十千米以外有两个数据中心,在100千米异地之外有另个灾备中心,保证了机房的高可用。另外包括网络、主机,其实架构上是这样的,至少说你的交换机网络都有备份,一个倒了之后,另外一个须要替换上去。oracle

img

下面进入咱们的重点,基于数据复制的高可用,首先介绍一下备份,备份确实是很是重要的,并且备份是一个实在没办法最后的一个保障,因此说建议你们无论是在云上用的业务,仍是本身的IDC尽可能作好备份。

MySQL备份基本上是这两种:逻辑备份、物理备份。逻辑备份一般使用官方的MySQLDump与第三方工具MyDumper,MyDumper优点在于多线程备份,速率快。物理备份使用Percona的xtrabackup,能够不落盘,经过基于流式并发与压缩,生产出成功率较高、速率较快而且暂用存储空间较低的备份。最后一种就是快照,咱们腾讯云的基础版的备份就是经过快照生成的。

那基于数据复制方式,通常是主从两个节点,数据怎么保证一致性呢?实际上是经过复制协议进行数据传输,经过Switch切换保证故障之后服务可以尽快恢复。右边的图基本和腾讯云MySQL差很少的架构,咱们采用了一主一从的方式,从节点只负责故障的转移,当主节点挂了之后,经过自动故障探测与自动切换,从而作到业务尽快恢复。另外针对读写分离,腾讯云MySQL现能够支持一主挂5个只读节点。

下面介绍一下复制,在介绍复制以前有必要介绍一个重要的概念:binlog,binlog是二进制文件,主要记录用户对数据库更新的sql信息,binlog是什么样子呢?它是在磁盘上是这个样子,使用show binlog events后它是这样的,里面会记录一些元信息,好比位点、事件等等,咱们经过MySQL官方解析工具mysqlbinlog解析后是这样的,里面sql语句是使用base64编码的,解码后是这样的,能够看到这里是条插入语句。那何时写binlog呢?你们来看这个图,咱们知道事务提交有两个阶段:prepare与commit,请问是哪一个阶段写binlog呢?binlog实际上是在prepare后commit前写入的,同时写事务过程当中,会产生redolog与undolog,那这二者有什么区别呢?咱们知道MySQL是多引擎的关系型数据库,binlog是MySQL Server层的日志,而redolog是MySQL引擎InnoDB层的日志;另一个不一样是二者写入时机不一样,redolog是prepare阶段每执行sql语句就写redo了,而binlog是在prepare完commit前写的。那MySQL在主从架构下怎么保证数据一致性呢?众所众知,MySQL为了保证性能,数据是先写内存后落盘的。当你数据库运行的时候,发生了宕机,机器再次恢复的时候多是部分数据落盘了,部分未落盘。这时,mysql是找到binlog最新同步的位点或GTID,来肯定redolog或者undolog中哪些实例须要回滚,哪些事务须要重作。另外,在写日志的时候,好比redolog或binlog,MySQL为保证高性能,也是先写内存后落盘的,因此日志的落盘策略也会影响数据的一致性。为保证数据的一致性,建议你们将涉及日志的参数配置为“双1”,也就是如图上所示。

img

下面咱们来看看复制整个流程,其实很简单,Master经过dump线程将binlog落盘,在Slave上会有两个线程,分别是IO线程和SQL线程。IO线程接受来自Master的binlog并落地造成Relaylog,SQL线程并行读取relaylog中的sql信息,执行回放动做。通常来讲, 复制分三种:异步复制、半同步、强同步。这三者的区别在于什么时候将sql执行的结果反馈给客户端。异步复制,Master无论Slave,Master执行sql完毕后当即返回给客户端,这种方式性能最好,可是存在数据不一致的可能;强同步呢,Master彻底关心Slave,等待Slave将relaylog回放后才返回给客户端,这种方式可以保证数据强一致,可是其性能有必定损耗;半同步则是Master部分关心Slave,认为只要binlog传输到Slave侧,落为relaylog后,便可以返回给客户端了。半同步是一种兼顾的实现,一方面保证数据一致性,另外一方面兼顾了数据库的性能。

img

在复制过程当中,咱们常常遇到延迟问题,你们看图中所示,复制经历三个阶段:Dump线程落盘binlog、IO线程落盘relaylog、以及SQL线程回放,请问三个步骤里面哪一个步骤是一个瓶颈?是SQL线程,是由于SQL线程在回放日志过程当中是串行执行sql的,而Master对外是并行提供服务的。因此这里瓶颈是SQL线程。你们可用经过开启并行复制来解决延迟问题,MySQL5.6基于库级别并行复制;MySQL 5.7基于逻辑时钟并行复制,也就是表级别的并行;而MySQL8.0则是行级别的并行复制,粒度更细,复制效率更高。

img

刚才是说在协议级别进行复制,其实还有一种方式是块级别的数据复制,其不关心上层是什么,只须要保证在磁盘层面数据复制便可。固然这种方式的话,应用的比较少。说完复制后,我们来讲一下切换,其实MySQL官方以前并无提供故障自动发现与转移的能力,基本上靠第三方工具来实现。

img

第一种是Keepalived,Master和Slave相互探测对方,时刻询问对方存活状态。当出现网络抖动或者网络出现问题的时候,可能会出现脑裂问题,变成了两主,数据就写错乱了。第二种就是MMM的方式, M1M2互为主备,再加上一个Slave节点作冗余。从图上看,虽然是双主,但该模式下同一时间点下只能有一个节点能够写,当发现这个主写节点出现故障,会将vip切换到另外一个主上比。总体看,这种方式比较老,问题比较多。第三种是MHA,其应用普遍,这种方式是由复制组与管理节点组成,每一个复制组里是由至少三个数据节点组成,数据节点上部署监控agent,定时上报到管理节点,当主节点出现问题时,由管理节点裁决是否切换到从节点。腾讯云是本身实现了一套故障检测,结构如右边的图,由高可用保证的Monitor节点来进行故障检测与切换。另外,目前咱们还在作MySQL高可用的重构,届时可以作到故障检测恢复30秒钟之内,大大提升了高可用。

img

下面咱们来讲下集群的高可用架构,比较有名的就是PXC、MGC、MGR,PXC和MGC是结构比较相似,MGR是官方提供的,具备故障转移的高可用架构。大致的层级是这样的,MGR以插件的形式存在的,MGR主要是把复制协议进行改造,由于MGR支持多活,因此这里另外一个重点是冲突检测,若多个节点同时写同一主键时,依照哪一个为准呢?MGR是采用基于Paxos协议实现的冲突检测。下面,咱们大体看下结构,MGR是支持多个节点写,即多活,支持某个节点挂了后自动剔除,恢复后自动加入集群。这张图是介绍一下MGR数据流逻辑,图上有三个节点构成最小MGR集群。假设DB1有一次写提交,在Prepare阶段,MGR插件会生成一个叫WriteSet的集合,并将其广播给其余节点。这个WriteSet集合包含这次提交的binlog和更新的惟一键,此惟一键由db名、表名和主键组成。这里能够看出MGR有个限制,表中必需要有主键,要不没法进行冲突检测。咱们再说回来当节点收到这一信息时,会进行比对,每一个节点都有一个缓存,保存当前同步状况,即惟一键对应的GTID SET。经过比对后将结果返回给DB1,只要多于半数的节点返回说OK,能够提交,那DB1接下来就会执行binlog的落盘操做,而后返回OK到客户端。其余节点则执行写Relaylog的动做,接下来进行回放的动做。若多数节点返回冲突,DB1则执行回滚操做,其余节点会drop掉复制过来的binlog。

其实PXC和MGC思路是差很少,应该说是MGR借鉴的,由于PXC和MGC是比较早就出来的,这里大同小异,主节点将WriteSet写集合广播出去,广播完后进行验证与裁决。

img

最后咱们说一下NewSQL高可用架构,首先对AWS表示致敬,孵化出很是优秀的NewSQL产品-Aurora。那Aurora是怎么产生出来的呢?这与AWS数据库架构有关。咱们来看看这个图,AWS数据库是架构在虚拟机与云盘上的,咱们都知道MySQL的log比较多,因此不少IO是经过耗时较高的网络来完成的,所以AWS这种架构网络IO是它的瓶颈,性能也跑不上去。在此基础上,咱们来认识下Aurora。

Aurora是计算与存储分离的架构,典型的share disk 的结构。底层存储采用6副本,部署在三个不一样的AZ上,能够保证一个AZ挂了,或者至多两个AZ的一个副本丢失的状况下数据不丢失,业务能够正常对外服务。Aurora的理念是“日志即数据库”,其把MySQL存储层进行了完全的改造,摒弃了不少LOG,只留下了Redolog,具有将redolog转换到Innodb page的能力。经过这种方式,Aurora宣称其减小至少85%比例的IO。另外其把备份和回档下沉到存储节点,使得备份恢复更快并获得保障。Aurora总体感受相对比较接地气,成本相对比较低。

另外一个就是阿里云的Polar,理念和AWS不一样,阿里云以为将来网络不是问题,将来网络能够接近总线的质量,因此是架构在RDMA网络的机房里,日志方面大动做较少,保证后续MySQL社区新特性可快速迭代近来。Polardb也是share disk的架构,其存储节点是通ParallelRaft协议保证数据的完备性。可见这也是个伟大的架构,可是相对来讲成本比较高一些。

咱们腾讯云本身的NewSQL在研发中,只是目前尚未正式上线,咱们的名字叫CynosDB,相比来讲咱们的理念是兼顾二者,将来在高网络新硬件的基础实施下,会发挥更大的性能,更稳健的服务和更高的可用性。请你们拭目以待。

本次个人分享就到此为止。更多数据库前沿技术可关注 咱们公众号:腾讯云数据库CDB

img

Q & A

Q:我想问一下在腾讯游戏的高并发行业里面,咱们主要采用哪一种架构?

A:腾讯内部有不少自研项目,但基本上咱们是基于数据复制的方式。内部有phxsql等分布式集群架构。

Q:如何在高并发状况下,保证总库的定延时呢?

A:能够开启并行复制,业务作分库分表,分散到多个实例上。

Q:好比说像游戏类的,在游戏高峰期的话会有不少人同时在线,这种状况下怎么在后台看数据呢?

A:能够对比较热的数据进行分层,前一层能够经过KV方式缓存,好比Redis,来提升热数据的读取,后一层使用MySQL,按期将数据同步落盘。

Q:这种状况下怎么保证数据库是一致的呢?

A:写数据能够不通过KV缓存,直接写MySQL数据库,读取时,缓存内没有数据,须要从DB中捞取出来。另外,KV缓存也有落地能力,非关键数据也能够不使用MySQL落地。

相关阅读 【每日课程推荐】机器学习实战!快速入门在线广告业务及CTR相应知识

此文已由做者受权腾讯云+社区发布,更多原文请点击

搜索关注公众号「云加社区」,第一时间获取技术干货,关注后回复1024 送你一份技术课程大礼包!

海量技术实践经验,尽在云加社区

相关文章
相关标签/搜索