本文提供mysql组复制相关的背景信息。
创建容错系统的最常用方式是采用组件冗余方式,换句话说,就是组件能被移除且系统应该继续如期操作。这产生了一系列将系统复杂度上升到不同等级的挑战。特别是,复制数据库必须处理几个而非一个服务器维护和管理的事实。然而,因为服务器一起合作创建了几个其他经典分布式系统问题需要处理的组,像网络分区(network partitioning)或脑裂场景(split brain)。
因此,最终挑战是将数据库和数据复制逻辑与几个服务器一致简单合作逻辑相融合。换句话说,使得几个服务器的系统状态和系统上发生的数据及改变达成一致。这能总结为让所有服务器的数据库状态转换达成一致,以便所有服务器作为单个数据库工作,或者最终达成同样状态。这意味着它们需要作为(分布式)状态机进行操作。
mysql组复制通过服务器间的密切合作支持分布式状态机复制。当服务器成为同一个组的一部分时,它们自动进行合作。mysql复制组能以自动选举主库的单主模式进行操作,其中,任意时刻只有一个服务器接受更新。此外,对更高级用户,mysql复制组能按照多主模式部署,其中,所有服务器都能接受更新,及时同时发布更新。实现该功能以应用必须避免该种部署方式产生的限制作为代价。
有一个内建组成员服务保持所有服务器在任何时间点的组一致和可用视图。服务器能离开和加入该组,且该视图也会做相应更新。有时服务器能意外离开该组,这种场景中,失败探测机制会探测到并通知该组视图已发生改变。所有这一切都是自动的。
事务提交时,复制组的大部分服务器必须对指定事务的全局顺序达成一致。决定提交或终止一个事务由每个服务器分别完成,但所有服务器做出同样的决定。如果有网络分区,导致成员们不能达成一致的分裂,直到该问题得以解决系统才会继续进行。然而,也有内建的、自动化的、脑裂保护机制。
所有这些都靠组通信协议(Group Communication System(GCS))进行驱动。这些提供了一个失败探测机制,一个组成员服务及安全完全的排序信息交付。所有这些是创建一个确保数据在组内服务器间进行一致复制的系统。该技术的核心在于Paxos算法的实施。其扮演组通信引擎。
一.复制技术
深入了解mysql组复制技术前,该部分对一些后台概念和工作原理概览做一下介绍。这为帮助理解组复制所需的前提及经典异步mysql复制和组复制间的差别提供一些上下文。其为shared-nothing架构。
1.主次复制(Primary-Secondary Replication)
图1-1 mysql异步复制
也有半同步复制,其为该协议增加了一个同步步骤。这意味着主库提交时等待二级库确认已经收到该事务。仅收到二级库的确认后,主库才恢复提交操作。
图1-2 mysql半同步复制
上述两张图中,您能看到经典异步mysql复制协议图(及其半同步变体)。斜线箭头表示服务器间交换的信息或服务器和客户端应用间交换的信息。
2.组复制
组复制是一种能用于实施容错系统的技术。复制组时一套通过信息传递相互交互的服务器。通信层提供一套类似原子信息和总序信息交付的保证。这些是很有力的属性,其将转换为很有用的、人们能用其构建更高级数据库复制解决的抽象层。
mysql组复制构建于这些属性和抽象的顶端,并实施一个多主随处更新的复制协议。实际上,复制组由多个服务器组成,且组内的每个服务器可以独立的执行事务。但所有的读写事务仅在得到组批准后提交。只读事务与组合作而立即提交。换句话说,对任何需要组决定是否提交的读写事务,提交操作不是一个起源服务器的单边决定。确切的说,当事务在起源服务器上准备提交时,该服务器自动广播该写值(改变的数据行)和通信写集(被更新数据行的唯一标识),接着,该事务的全局总序被建立。最终,这意味着所有服务器按照同样顺序接收相同一套事务。结果,所有服务器按照同样的顺序应用这套改变,所以,它们在组内保持一致。
然而,不同服务器上并行执行的事务也许会发生冲突。这些冲突通过检查两个不同但并发执行事务的写集进行探测,该过程称为认证。如果在不同服务器上执行更新相同数据行的两个并发事务,发生了冲突。解决过程声明排在前面的事务在所有服务器上提交,而排在后面的事务终止,这样,其在起源服务器上回滚并被组内的其他服务器删除。这实际上是一个分布式先提交获胜的规则。
图1-3 mysql组复制协议
最后,组复制是一个shared-nothing复制方案,其组内每个服务器都有其自己的一整套数据拷贝。
上图描述了mysql组复制协议,且通过与mysql复制(或甚至mysql本同步复制)比较,您能看到某些差别。注意,出于清晰起见,某些底层共识和Paxos相关信息在该图中略去。
二.组复制使用场景
组复制通过在一整套服务器间复制系统状态使得能创建冗余的容错系统。因此,及时某些服务器失败,只要不是所有或大部分服务器失败,系统还是可用的,且其最大可能的后果就是性能或扩展性的降级,但其还是可用的。
服务器失败被隔离和独立。它们被组成员服务跟踪,该服务依赖于当任何服务器因为自愿或意外终止离开组时,能发送信号的分布式错误探测器。有分布式恢复过程确保当服务器加入组时其被自动更新到最新日期。不必做服务器失败切换,多主随处更新特性确保单服务器失败事件中更新不会被阻塞。所以,mysql组复制保证数据库服务连续可用。
理解虽然数据库服务是可用的,在服务器崩溃事件中,那些已连接到该服务器的客户端必须重定向或失败切换到不同的服务器是非常重要的。这不是mysql组复制试图解决的问题。连接器,负载均衡器,路由或某种形式的中间件更适合处理该类问题。
总之,mysql组复制支持高可用、高弹性、可靠的mysql服务。
1.使用场景举例
下述例子是组复制的典型使用场景:
1)弹性复制:需要变动很大的复制基础设施的环境,其中服务器数目必须动态增加或缩减,且尽可能的没有副作用。例如:云数据库服务。
2)高可用分片:分片取得写水平扩展的流行方法。用mysql组复制实施高可用分片,其中每个分片映射到一个复制组。
3)替代主备复制:在某些场景,用单主服务器会带来单点冲突。某些场景下,写整个复制组也许更具扩展性。
4)自主系统:另外,您能纯粹为了内建到复制协议的自动化而部署mysql组复制。
三.组复制细节
该部分描述有关组复制基于的某些服务细节。
1.失败探测
有一个失败探测机制能发现和报告哪个服务器沉默且因此而认为其已死掉。在高级别,失败探测器时一个分布式服务,其能提供有关哪些服务器也许已死掉(怀疑)的信息。稍后如果组一直认为怀疑可能是真的,那么,组决定指定服务器确实已失败。这意味着组中剩余成员采取一个协同决定来排除指定成员。
当服务器没反应时会触发怀疑。当服务器A在指定期间没有收到来自服务器B的信息时,发生超时并产生一个怀疑。
如果一个服务器与组内其他成员隔离开,那么其怀疑所有其他服务器都已失败。不能与组(因为其不能保证达到法定人数)达成一致,其怀疑并不会有结果。当服务器以这种方式与组隔离时,其不能执行任何本地事务。
2.组成员
mysql组复制依赖于一个组成员服务。这被建进插件。其定义哪些服务器在线并参与组。在线服务器列表通常被参考为一个视图。所以,组内的每个服务器有一个一致性视图,该视图显示指定时刻活跃参与该组的成员。
服务器不仅对事务提交,而且也对当前视图达成一致。因此,如果服务器同意一台新服务器加入组,那么,组自身必须重新配置以将新服务器整合进来,并触发一个视图改变。相反情况也会发生,如果一台服务器离开该组,无论是否自愿,那么,该组将动态重新配置并触发一个视图改变。
但请注意,当一个成员自愿离开时,其首先初始化一个动态组重配置。这将触发一个过程,期间,所有成员必须就不包含该离开服务器的视图达成一致。但是,如果一个成员非自愿离开(例如:其意外停止或网络连接宕掉),则失败探测机制认识到该事实并提议一个重配置,这将排除失败的成员。如上所述,这将需要组内大部分服务器达成一致。如果该组不能达成一致(例如:其分区场景中没有多数服务器在线),那么,系统不能动态改变配置,因此阻塞以阻止发生脑裂场景。最终,这意味着管理员需要介入和修复该问题。
3.容错
mysql组复制基于Paxos分布式算法实施以支持服务器间的分布式合作。这样,其要求大部分服务器活动来达到法定人数并作出决定。这对系统能容忍而不会折衷系统整体功能的失败服务器数有直接影响。容忍f个失败服务器的服务器数为n=2*f+1。
实践中,这意味着为了容忍失败,组必须有3个服务器。这样,如果一台服务器失败,还有两台服务器形成大部分(3台中的2台),并允许系统继续自动决定和运行。然而,如果第2台服务器非自愿失败了,那么,该组(仅剩1台服务器)将会阻塞,因为没有多数服务器来达成决定。