MySQL8 中文参考(八十)(4)https://developer.aliyun.com/article/1565890
第二十章 组复制
本章介绍了 MySQL Group Replication 以及如何安装、配置和监控组。MySQL Group Replication 可以创建弹性、高可用、容错的复制拓扑。
组可以以单一主模式运行,具有自动主选举功能,每次只有一个服务器接受更新。另外,组也可以以多主模式部署,所有服务器都可以接受更新,即使它们同时发出。
有一个内置的组成员服务,保持组的视图在任何给定时间点对所有服务器一致和可用。服务器可以离开和加入组,视图会相应更新。有时服务器可能意外离开组,此时故障检测机制会检测到并通知组视图已更改。这一切都是自动的。
Group Replication 保证数据库服务持续可用。然而,重要的是要理解,如果组中的一个成员不可用,连接到该组成员的客户端必须被重定向或故障转移到组中的另一台服务器,使用连接器、负载均衡器、路由器或某种中间件。Group Replication 没有内置的方法来做到这一点。例如,参见 MySQL Router 8.0。
组复制作为 MySQL Server 的一个插件提供。您可以按照本章的说明在您想要的每个服务器实例上配置插件,启动组,并监视和管理组。部署 MySQL 服务器实例组的另一种方法是使用 InnoDB Cluster。
提示
要部署多个 MySQL 实例,您可以使用 InnoDB Cluster,它使您能够轻松管理一组 MySQL 服务器实例在 MySQL Shell 中。InnoDB Cluster 将 MySQL Group Replication 包装在一个编程环境中,使您可以轻松部署一组 MySQL 实例以实现高可用性。此外,InnoDB Cluster 与 MySQL Router 无缝接口,使您的应用程序可以连接到集群而无需编写自己的故障转移过程。然而,对于不需要高可用性的类似用例,您可以使用 InnoDB ReplicaSet。有关 MySQL Shell 的安装说明,请参见这里。
本章结构如下:
- 第 20.1 节,“组复制背景” 介绍了组和组复制的工作原理。
- 第 20.2 节,“入门指南” 解释了如何配置多个 MySQL Server 实例以创建一个组。
- 第 20.3 节,“需求和限制” 解释了组复制的架构和设置需求以及限制。
- 第 20.4 节,“监控组复制” 解释了如何监控一个组。
- 第 20.5 节,“组复制操作” 解释了如何操作一个组。
- 第 20.6 节,“组复制安全” 解释了如何保护一个组。
- 第 20.7 节,“组复制性能和故障排除” 解释了如何为一个组调整性能。
- 第 20.8 节,“升级组复制” 解释了如何升级一个组。
- 第 20.9 节,“组复制变量” 是特定于组复制的系统变量的参考。
- 第 20.10 节,“常见问题” 提供了关于部署和操作群组复制的一些技术问题的答案。
20.1 Group Replication 背景
原文:
dev.mysql.com/doc/refman/8.0/en/group-replication-background.html
20.1.1 Replication Technologies
20.1.2 Group Replication Use Cases
20.1.3 Multi-Primary and Single-Primary Modes
20.1.4 Group Replication Services
20.1.5 Group Replication Plugin Architecture
本节提供了关于 MySQL Group Replication 的背景信息。
创建容错系统最常见的方法是通过使组件冗余化,换句话说,组件可以被移除而系统应该继续按预期运行。这带来了一系列挑战,将这些系统的复杂性提升到一个全新的水平。具体来说,复制的数据库必须处理这样一个事实,即它们需要维护和管理多台服务器,而不仅仅是一台。此外,由于服务器合作创建组,因此必须处理一些其他经典的分布式系统问题,例如网络分区或脑裂场景。
因此,最终的挑战是将数据库和数据复制的逻辑与多台服务器以一致且简单的方式协调的逻辑融合在一起。换句话说,让多台服务器就系统状态和每次系统经历的变化的数据达成一致意见。这可以总结为使服务器就每个数据库状态转换达成一致意见,以便它们都像一个单一数据库一样前进,或者最终收敛到相同的状态。这意味着它们需要作为(分布式)状态机运行。
MySQL Group Replication 提供了具有强大协调功能的分布式状态机复制。当服务器属于同一组时,它们会自动协调。该组可以在单主模式下运行,具有自动主选举,每次只有一台服务器接受更新。或者,对于更高级的用户,该组可以部署在多主模式下,其中所有服务器都可以接受更新,即使它们同时发出。这种功能是以应用程序必须解决这些部署所施加的限制为代价的。
存在一个内置的组成员服务,使组的视图在任何给定时间点对所有服务器保持一致和可用。服务器可以离开和加入组,视图会相应更新。有时服务器可能意外离开组,此时故障检测机制会检测到这一点,并通知组视图已更改。这一切都是自动的。
要使交易提交,大多数组成员必须就给定交易在全局交易序列中的顺序达成一致。决定提交或中止交易是每个服务器单独完成的,但所有服务器都做出相同的决定。如果出现网络分区,导致成员无法达成一致,那么系统将在解决此问题之前不会继续进行。因此,系统还具有内置的、自动的、防止脑裂的机制。
所有这些都由提供的群组通信系统(GCS)协议驱动。这些协议提供了故障检测机制、群组成员服务以及安全和完全有序的消息传递。所有这些属性对于创建一个确保数据在服务器组中一致复制的系统至关重要。在这项技术的核心是 Paxos 算法的实现。它充当群组通信引擎。
20.1.1 复制技术
原文:
dev.mysql.com/doc/refman/8.0/en/group-replication-replication-technologies.html
20.1.1.1 源到副本复制
20.1.1.2 集群复制
在深入了解 MySQL 集群复制之前,本节介绍了一些背景概念以及工作原理的概述。这提供了一些背景信息,帮助理解集群复制所需的条件以及经典异步 MySQL 复制与集群复制之间的区别。
原文:
dev.mysql.com/doc/refman/8.0/en/group-replication-primary-secondary-replication.html
20.1.1.1 源到副本复制
传统的 MySQL 复制 提供了一种简单的源到副本的复制方法。源是主服务器,副本是从服务器。源应用事务,提交它们,然后稍后(因此是异步的)将它们发送到副本以重新执行(在基于语句的复制中)或应用(在基于行的复制中)。这是一个共享无系统,所有服务器默认都有完整的数据副本。
图 20.1 MySQL 异步复制
还有半同步复制,它在协议中添加了一个同步步骤。这意味着主服务器在应用时等待副本确认已接收事务。只有在副本确认接收事务后,主服务器才恢复提交操作。
图 20.2 MySQL 半同步复制
在这两幅图中有一个经典的异步 MySQL 复制协议的图示(以及其半同步变体)。不同实例之间的箭头代表服务器之间或服务器与客户端应用程序之间交换的消息。
原文:
dev.mysql.com/doc/refman/8.0/en/group-replication-summary.html
20.1.1.2 Group Replication
Group Replication 是一种可用于实现容错系统的技术。复制组是一组每个服务器都拥有自己完整数据副本的服务器(共享无内容复制方案),并通过消息传递相互交互。通信层提供了一组保证,如原子消息和总顺消息传递。这些是非常强大的属性,可以转化为非常有用的抽象,可以用来构建更高级的数据库复制解决方案。
MySQL Group Replication 建立在这些属性和抽象之上,并实现了一个多源更新的复制协议。一个复制组由多个服务器组成,组中的每个服务器可以随时独立执行事务。然而,所有读写事务只有在组批准后才提交。换句话说,对于任何读写事务,组都需要决定是否提交,因此提交操作不是来自原始服务器的单方面决定。只读事务在组内不需要协调,立即提交。
当一个读写事务在原始服务器准备提交时,服务器会原子地广播写入值(已更改的行)和相应的写入集(已更新行的唯一标识符)。由于事务通过原子广播发送,组中的所有服务器都会接收到事务,或者都不会接收到。如果它们接收到了,那么它们都会按照与之前发送的其他事务相同的顺序接收它。因此,所有服务器以相同的顺序接收相同的事务集,并为事务建立了全局总顺序。
然而,在不同服务器上并发执行的事务之间可能存在冲突。这种冲突是通过检查和比较两个不同且并发事务的写入集来检测的,在一个称为认证的过程中。在认证过程中,冲突检测是在行级别进行的:如果两个并发事务,在不同服务器上执行,更新了相同的行,则存在冲突。冲突解决程序规定,首先被排序的事务在所有服务器上提交,而第二个被排序的事务中止,因此在原始服务器上回滚,并被组中的其他服务器丢弃。例如,如果 t1 和 t2 在不同站点并发执行,都更改了相同的行,并且 t2 在 t1 之前被排序,那么 t2 赢得冲突,t1 被回滚。实际上,这是一个分布式的“先提交者获胜”规则。请注意,如果两个事务往往会发生冲突,那么将它们放在同一服务器上开始是一个好的做法,这样它们有机会在本地锁管理器上同步,而不是由于认证的结果而被回滚。
为了应用和外部化经过认证的事务,集群复制允许服务器偏离事务的约定顺序,如果这不会破坏一致性和有效性。集群复制是一个最终一致性系统,意味着一旦传入流量减少或停止,所有组成员都具有相同的数据内容。在流量流动时,事务可以以稍微不同的顺序外部化,或者在某些成员之前外部化。例如,在多主模式下,一个本地事务可能会在认证后立即外部化,尽管一个在全局顺序中较早的远程事务尚未被应用。当认证过程已经确定事务之间没有冲突时,这是允许的。在单主模式下,在主服务器上,存在一个小概率,即并发的、非冲突的本地事务可能会按照与集群复制约定的全局顺序不同的顺序提交和外部化。在不接受来自客户端的写入的从属服务器上,事务总是按照约定的顺序提交和外部化。
以下图描述了 MySQL 集群复制协议,并通过将其与 MySQL 复制(甚至 MySQL 半同步复制)进行比较,您可以看到一些差异。为了清晰起见,这张图片中省略了一些底层共识和 Paxos 相关的消息。
图 20.3 MySQL 集群复制协议
20.1.2 Group Replication 使用案例
原文:
dev.mysql.com/doc/refman/8.0/en/group-replication-use-cases.html
Group Replication 可以让您创建具有冗余性的容错系统,通过将系统状态复制到一组服务器。即使其中一些服务器随后失败,只要不是全部或大多数,系统仍然可用。根据失败的服务器数量,群组可能会有性能或可伸缩性下降,但仍然可用。服务器故障是隔离的和独立的。它们由一个依赖于分布式故障检测器的群组成员服务跟踪,该故障检测器能够在任何服务器离开群组时发出信号,无论是自愿离开还是由于意外停止。有一个分布式恢复过程,确保当服务器加入群组时,它们会自动更新。不需要服务器故障转移,而多源更新到处的特性确保即使单个服务器故障,更新也不会被阻塞。总之,MySQL Group Replication 保证数据库服务持续可用。
重要的是要理解,尽管数据库服务可用,但在发生意外服务器退出时,连接到它的客户端必须被重定向或故障转移到另一台服务器。这不是 Group Replication 试图解决的问题。连接器、负载均衡器、路由器或某种形式的中间件更适合处理这个问题。例如,请参阅 MySQL Router 8.0。
总结一下,MySQL Group Replication 提供了一个高可用、高弹性、可靠的 MySQL 服务。
提示
要部署多个 MySQL 实例,您可以使用 InnoDB Cluster,它使您能够在 MySQL Shell 中轻松管理一组 MySQL 服务器实例。InnoDB Cluster 在一个编程环境中封装了 MySQL Group Replication,使您可以轻松部署一组 MySQL 实例以实现高可用性。此外,InnoDB Cluster 与 MySQL Router 无缝接口,使您的应用程序可以连接到集群而无需编写自己的故障转移过程。然而,对于不需要高可用性的类似用例,您可以使用 InnoDB ReplicaSet。MySQL Shell 的安装说明可以在这里找到。
示例用例
以下示例是 Group Replication 的典型用例。
- 弹性复制 - 需要非常灵活的复制基础设施的环境,在这种环境中,服务器数量必须能够动态增长或收缩,并且副作用尽可能少。例如,云端的数据库服务。
- 高可用碎片 - 分片是实现写扩展的流行方法。使用 MySQL 集群复制来实现高可用碎片,其中每个碎片映射到一个复制组。
- 替代异步源-副本复制 - 在某些情况下,使用单个源服务器会使其成为一个争用点。在某些情况下,向整个组写入可能更具可扩展性。
- 自主系统 - 此外,您可以纯粹为内置于复制协议中的自动化部署 MySQL 集群复制(在本章和前几章中已经描述)。
20.1.3 多主和单主模式
20.1.3.1 单主模式
20.1.3.2 多主模式
Group Replication 可以在单主模式或多主模式下运行。该组的模式是一个全组配置设置,由group_replication_single_primary_mode
系统变量指定,所有成员必须相同。ON
表示单主模式,这是默认模式,OFF
表示多主模式。不可能让组的成员以不同模式部署,例如一个成员配置为多主模式,而另一个成员处于单主模式。
在 Group Replication 运行时无法手动更改group_replication_single_primary_mode
的值。从 MySQL 8.0.13 开始,您可以使用group_replication_switch_to_single_primary_mode()
和group_replication_switch_to_multi_primary_mode()
函数在 Group Replication 仍在运行时将组从一种模式转换到另一种模式。这些函数管理更改组模式的过程,并确保数据的安全性和一致性。在早期版本中,要更改组的模式,您必须停止 Group Replication 并在所有成员上更改group_replication_single_primary_mode
的值。然后执行组的完全重启(由具有group_replication_bootstrap_group=ON
的服务器引导)以实施对新操作配置的更改。您无需重新启动服务器。
无论部署模式如何,Group Replication 不处理客户端故障转移。这必须由中间件框架(如 MySQL Router 8.0)、代理、连接器或应用程序本身处理。
原文:
dev.mysql.com/doc/refman/8.0/en/group-replication-single-primary-mode.html
20.1.3.1 单主模式
在单主模式下(group_replication_single_primary_mode=ON
),组具有一个被设置为读写模式的单主服务器。组中的所有其他成员都被设置为只读模式(使用super_read_only=ON
)。主服务器通常是第一个引导组的服务器。加入组的所有其他服务器都会了解主服务器并自动设置为只读模式。
在单主模式下,组复制要求只有一个服务器写入组,因此与多主模式相比,一致性检查可以更宽松,DDL 语句不需要额外小心处理。选项group_replication_enforce_update_everywhere_checks
用于启用或禁用组的严格一致性检查。在部署单主模式或将组更改为单主模式时,必须将此系统变量设置为OFF
。
被指定为主服务器的成员可以通过以下方式更改:
- 如果现有的主服务器离开组,无论是自愿还是意外,新的主服务器将自动选举产生。
- 您可以使用
group_replication_set_as_primary()
函数指定特定成员作为新的主服务器。 - 如果使用
group_replication_switch_to_single_primary_mode()
函数将运行在多主模式下的组更改为单主模式,新的主服务器将自动选举产生,或者您可以通过该函数指定新的主服务器。
这些函数只能在所有组成员运行 MySQL 8.0.13 或更高版本时使用。当新的主服务器自动选举产生或手动指定时,它会自动设置为读写模式,其他组成员保持为从服务器,因此为只读模式。图 20.4, “新主服务器选举”展示了这个过程。
图 20.4 新主服务器选举
当新的主要被选举或任命时,它可能有一些在旧主要上已应用但尚未应用在此服务器上的更改积压。在这种情况下,直到新的主要赶上旧的主要,读写事务可能会导致冲突并被回滚,只读事务可能会导致过时读取。如果激活并正确调整了 Group Replication 的流量控制机制,它将减少快速和慢速成员之间的差异,从而降低发生这种情况的机会。有关流量控制的更多信息,请参见第 20.7.2 节,“流量控制”。从 MySQL 8.0.14 开始,您还可以使用group_replication_consistency
系统变量来配置组的事务一致性级别,以防止此问题。设置BEFORE_ON_PRIMARY_FAILOVER
(或任何更高的一致性级别)将新事务保留在新选举的主要上,直到积压被应用。有关事务一致性的更多信息,请参见第 20.5.3 节,“事务一致性保证”。如果组未使用流量控制和事务一致性保证,等待新主要应用其与复制相关的中继日志再将客户端应用程序重新路由到它是一个良好的做法。
20.1.3.1.1 主要选举算法
自动主要成员选举过程涉及每个成员查看组的新视图,对潜在的新主要成员进行排序,并选择符合条件的最合适的成员。每个成员在本地做出自己的决定,遵循其 MySQL Server 版本中的主要选举算法。因为所有成员必须达成相同的决定,如果其他组成员运行较低版本的 MySQL Server,则成员会调整其主要选举算法,以使其与组中具有最低 MySQL Server 版本的成员具有相同的行为。
成员在选举主要时考虑的因素按顺序如下:
- 考虑的第一个因素是哪个成员或哪些成员正在运行最低版本的 MySQL 服务器。如果所有组成员都在运行 MySQL 8.0.17 或更高版本,则首先按照其发布的补丁版本对成员进行排序。如果有任何成员正在运行 MySQL 服务器 5.7 或 MySQL 8.0.16 或更低版本,则首先按照其发布的主要版本对成员进行排序,而忽略补丁版本。
- 如果有多个成员运行最低版本的 MySQL 服务器,则考虑的第二个因素是每个成员的成员权重,由成员上的
group_replication_member_weight
系统变量指定。如果组中的任何成员正在运行 MySQL 服务器 5.7,在那里这个系统变量不可用,则忽略此因素。group_replication_member_weight
系统变量指定一个范围为 0-100 的数字。所有成员的默认权重为 50,因此将权重设置为低于此值以降低其排序,将权重设置为高于此值以增加其排序。您可以使用此加权函数来优先使用更好的硬件或确保在主服务器计划维护期间故障转移到特定成员。 - 如果有多个成员运行最低版本的 MySQL 服务器,并且其中有多个成员具有最高的成员权重(或正在忽略成员权重),则考虑的第三个因素是每个成员生成的服务器 UUID 的词典顺序,由
server_uuid
系统变量指定。具有最低服务器 UUID 的成员被选择为主服务器。此因素充当保证和可预测的决定者,以便如果没有任何重要因素可以确定,则所有组成员达成相同的决定。
20.1.3.1.2 找到主服务器
要找出在单主模式下当前是主服务器的服务器,请使用performance_schema.replication_group_members
表中的MEMBER_ROLE
列。例如:
mysql> SELECT MEMBER_HOST, MEMBER_ROLE FROM performance_schema.replication_group_members; +-------------------------+-------------+ | MEMBER_HOST | MEMBER_ROLE | +-------------------------+-------------+ | remote1.example.com | PRIMARY | | remote2.example.com | SECONDARY | | remote3.example.com | SECONDARY | +-------------------------+-------------+
警告
group_replication_primary_member
状态变量已被弃用,并计划在将来的版本中删除。
或者使用group_replication_primary_member
状态变量。
mysql> SHOW STATUS LIKE 'group_replication_primary_member'
原文:
dev.mysql.com/doc/refman/8.0/en/group-replication-multi-primary-mode.html
20.1.3.2 多主模式
在多主模式(group_replication_single_primary_mode=OFF
)中,没有任何成员担任特殊角色。任何与其他组成员兼容的成员在加入组时被设置为读写模式,并且可以处理写事务,即使这些事务是并发发出的。
如果某个成员停止接受写事务,例如,出现意外服务器退出的情况,连接到该成员的客户端可以被重定向或故障转移至任何处于读写模式的其他成员。Group Replication 本身不处理客户端故障转移,因此您需要使用中间件框架(如 MySQL Router 8.0)、代理、连接器或应用程序本身来安排这一点。图 20.5,“客户端故障转移” 显示了客户端如何在成员离开组时重新连接到另一个组成员。
图 20.5 客户端故障转移
Group Replication 是一个最终一致性系统。这意味着一旦传入流量减少或停止,所有组成员都具有相同的数据内容。在流量流动时,事务可以在某些成员上外部化,然后在其他成员上,特别是如果某些成员的写吞吐量较低,则可能导致过时读取的可能性。在多主模式下,较慢的成员也可能积累过多的待认证和应用的事务,导致冲突和认证失败的风险增加。为了限制这些问题,您可以激活和调整 Group Replication 的流量控制机制,以最小化快速和慢速成员之间的差异。有关流量控制的更多信息,请参见第 20.7.2 节,“流量控制”。
从 MySQL 8.0.14 开始,如果您希望对组中的每个事务都有事务一致性保证,可以使用group_replication_consistency
系统变量来实现。您可以选择适合组工作负载和数据读写优先级的设置,考虑到增加一致性所需的同步对性能的影响。您还可以为单个会话设置系统变量,以保护特别关注并发性的事务。有关事务一致性的更多信息,请参见 Section 20.5.3, “Transaction Consistency Guarantees”。
20.1.3.2.1 事务检查
在多主模式下部署组时,会对事务进行检查以确保其与模式兼容。当在多主模式下部署 Group Replication 时,将进行以下严格的一致性检查:
- 如果在 SERIALIZABLE 隔离级别下执行事务,则在与组同步时,其提交将失败。
- 如果一个事务针对具有级联约束的外键的表执行,那么当与组进行同步时,其提交将失败。
这些检查由group_replication_enforce_update_everywhere_checks
系统变量控制。在多主模式下,该系统变量通常应设置为ON
,但可以通过将系统变量设置为OFF
来选择性地停用检查。在部署单主模式时,该系统变量必须设置为OFF
。
20.1.3.2.2 数据定义语句
在多主模式下部署 Group Replication 拓扑时,在执行数据定义语句时,也通常称为数据定义语言(DDL),需要注意。
MySQL 8.0 引入了对原子数据定义语言(DDL)语句的支持,其中完整的 DDL 语句要么作为单个原子事务提交,要么回滚。然而,DDL 语句,无论是否原子,都会隐式结束当前会话中的任何活动事务,就好像在执行该语句之前执行了COMMIT
一样。这意味着 DDL 语句不能在另一个事务内执行,在事务控制语句(如START TRANSACTION ... COMMIT
)内执行,或者与同一事务内的其他语句组合。
Group Replication 基于一种乐观的复制范式,其中语句会乐观地执行,如果需要则会回滚。每个服务器在未先获得组协议的情况下执行。因此,在多主模式下复制 DDL 语句时需要更加小心。如果对同一对象进行模式更改(使用 DDL)和对对象包含的数据进行更改(使用 DML),则这些更改需要在模式操作尚未完成并在所有地方复制之前通过同一服务器处理。如果未能这样做,当操作被中断或仅部分完成时可能导致数据不一致。如果组部署在单主模式下,则不会出现此问题,因为所有更改都通过同一服务器执行,即主服务器。
有关 MySQL 8.0 中原子 DDL 支持的详细信息,以及某些语句复制行为的变化,请参阅 第 15.1.1 节,“原子数据定义语句支持”。
20.1.3.2.3 版本兼容性
为了获得最佳兼容性和性能,组中的所有成员应该运行相同版本的 MySQL Server,因此也应该运行相同版本的 Group Replication。在多主模式下,这更为重要,因为所有成员通常会以读写模式加入组。如果一个组包含运行不止一个 MySQL Server 版本的成员,那么一些成员可能与其他成员不兼容,因为它们支持其他成员不支持的功能,或者缺少其他成员拥有的功能。为了防范这种情况,在新成员加入时(包括已升级并重新启动的前成员),该成员会对其与组中其他成员的兼容性进行检查。
这些兼容性检查的一个重要结果在多主模式下尤为重要。如果加入的成员运行的 MySQL Server 版本高于现有组成员运行的最低版本,它会加入组但保持为只读模式。(在单主模式下运行的组中,新添加的成员默认为只读模式。)运行 MySQL 8.0.17 或更高版本的成员在检查兼容性时会考虑发布的补丁版本。运行 MySQL 8.0.16 或更低版本,或 MySQL 5.7 的成员只考虑主要版本。
在以多主模式运行的组中,成员使用不同的 MySQL Server 版本,Group Replication 会自动管理运行 MySQL 8.0.17 或更高版本的成员的读写和只读状态。如果一个成员离开组,那些运行当前最低版本的成员会自动设置为读写模式。当您将以单主模式运行的组更改为以多主模式运行时,使用group_replication_switch_to_multi_primary_mode()
函数,Group Replication 会自动将成员设置为正确的模式。如果成员运行的 MySQL 服务器版本高于组中最低版本,则会自动将其置于只读模式,而运行最低版本的成员会置于读写模式。
有关组中版本兼容性的完整信息以及在升级过程中如何影响组行为,请参阅第 20.8.1 节,“在组中组合不同的成员版本”。
20.1.4 组复制服务
原文:
dev.mysql.com/doc/refman/8.0/en/group-replication-details.html
20.1.4.1 组成员资格
20.1.4.2 失效检测
20.1.4.3 容错性
20.1.4.4 可观察性
本节介绍了组复制构建的一些服务。
原文:
dev.mysql.com/doc/refman/8.0/en/group-replication-group-membership.html
20.1.4.1 群组成员
在 MySQL Group Replication 中,一组服务器形成一个复制组。群组有一个以 UUID 形式的名称。群组是动态的,服务器可以随时离开(自愿或非自愿)和加入。每当服务器加入或离开时,群组会自动调整自身。
如果一个服务器加入群组,它会通过从现有服务器获取缺失状态来自动更新自身。如果一个服务器离开群组,例如因为维护而关闭,剩余的服务器会注意到它已经离开,并自动重新配置群组。
Group Replication 具有一个群组成员服务,定义了哪些服务器在线并参与群组。在线服务器列表被称为视图。群组中的每个服务器在给定时间点都对哪些服务器是活跃参与群组的成员有一致的视图。
群组成员不仅必须就事务提交达成一致意见,还必须就当前视图达成一致。如果现有成员同意新服务器应该成为群组的一部分,群组将重新配置以将该服务器整合进去,从而触发视图更改。如果一个服务器离开群组,无论是自愿还是非自愿,群组会动态重新排列其配置,并触发视图更改。
当一个成员自愿离开群组时,首先启动动态群重新配置,在此期间,所有成员必须就没有离开的服务器达成新的共识。然而,如果一个成员非自愿离开群组,例如因为意外停止或网络连接中断,它无法启动重新配置。在这种情况下,Group Replication 的故障检测机制在短时间内识别出成员已经离开,并提出了一个没有失败成员的群组重新配置。与自愿离开的成员一样,重新配置需要群组中大多数服务器的同意。然而,如果群组无法达成一致意见,例如因为分区导致没有大多数服务器在线,系统无法动态更改配置,并阻止分裂脑的情况发生。这种情况需要管理员干预。
一个成员可能会短暂离线,然后在故障检测机制检测到其故障之前,尝试重新加入组,而在组被重新配置以移除该成员之前。在这种情况下,重新加入的成员会忘记其先前的状态,但如果其他成员向其发送旨在其崩溃前状态的消息,这可能会导致问题,包括可能的数据不一致性。如果处于这种情况的成员参与 XCom 的共识协议,它有可能导致 XCom 在同一共识轮中传递不同的值,因为在故障前后做出不同的决定。
为了应对这种可能性,在 MySQL 5.7.22 版本和 MySQL 8.0 版本中,Group Replication 会检查这样一种情况:当同一台服务器的新实例尝试加入组时,而其旧实例(具有相同的地址和端口号)仍然被列为成员。新实例将被阻止加入组,直到旧实例通过重新配置被移除。请注意,如果group_replication_member_expel_timeout
系统变量添加了等待时间,以允许成员在被驱逐之前重新连接到组,那么受到怀疑的成员在怀疑超时之前重新连接到组,可以作为其当前实例再次活跃在组中。当成员超过驱逐超时并被驱逐出组,或者当服务器上的 Group Replication 被STOP GROUP_REPLICATION
语句或服务器故障停止时,它必须作为新实例重新加入。
原文:
dev.mysql.com/doc/refman/8.0/en/group-replication-failure-detection.html
20.1.4.2 故障检测
Group Replication 的故障检测机制是一个分布式服务,能够识别组中的服务器是否与其他服务器通信,因此被怀疑处于停机状态。如果组的共识是怀疑可能是真实的,组将协调决定将该成员驱逐。驱逐一个不通信的成员是必要的,因为组需要大多数成员就交易或视图更改达成一致。如果一个成员不参与这些决定,组必须将其移除,以增加组中包含大多数正常工作成员的机会,从而可以继续处理交易。
在复制组中,每个成员与其他成员之间都有一条点对点通信通道,形成一个完全连接的图。这些连接由组通信引擎(XCom,一种 Paxos 变体)管理,并使用 TCP/IP 套接字。一个通道用于向成员发送消息,另一个通道用于接收来自成员的消息。如果一个成员在 5 秒内没有收到来自另一个成员的消息,它会怀疑该成员已经失败,并在自己的性能模式表replication_group_members
中将该成员的状态列为UNREACHABLE
。通常,两个成员会互相怀疑对方已经失败,因为它们彼此之间没有通信。但也有可能,尽管不太可能,成员 A 怀疑成员 B 已经失败,但成员 B 并没有怀疑成员 A 已经失败 - 可能是由于路由或防火墙问题。一个成员也可以怀疑自己。一个与组其他成员隔离的成员怀疑所有其他成员已经失败。
如果一个怀疑持续超过 10 秒,怀疑的成员会试图向组内其他成员传播其观点,即怀疑的成员有缺陷。只有当怀疑的成员是通知者时才会这样做,这是从其内部 XCom 节点编号计算出来的。如果一个成员实际上与组的其他成员隔离开来,它可能会尝试传播其观点,但这不会产生任何后果,因为它无法获得其他成员的多数同意。只有当一个成员是通知者时,怀疑持续时间足够长以传播到组的其他成员,并且其他成员同意时,怀疑才会产生后果。在这种情况下,怀疑的成员被标记为从组中驱逐,在group_replication_member_expel_timeout
系统变量设置的等待期过后,驱逐机制检测到并实施驱逐后被驱逐。
在网络不稳定且成员经常在不同组合中失去和重新建立连接的情况下,理论上可能导致一个组标记所有成员进行驱逐,之后该组将停止存在并需要重新设置。为了应对这种可能性,从 MySQL 8.0.20 开始,Group Replication 的 Group Communication System (GCS)跟踪已被标记为驱逐的组成员,并在决定是否存在多数时将其视为被怀疑成员的组。这确保至少有一个成员留在组内,使组能够继续存在。当一个被驱逐的成员实际上已被从组中移除时,GCS 将删除其被标记为驱逐的记录,以便该成员可以重新加入组(如果有可能)。
有关可以配置的 Group Replication 系统变量的信息,以指定工作组成员对故障情况的响应以及被怀疑已经发生故障的组成员采取的行动,请参见 Section 20.7.7, “Responses to Failure Detection and Network Partitioning”。
原文:
dev.mysql.com/doc/refman/8.0/en/group-replication-fault-tolerance.html
20.1.4.3 容错性
MySQL Group Replication 基于 Paxos 分布式算法的实现,提供服务器之间的分布式协调。因此,它需要大多数服务器处于活动状态才能达成法定人数,从而做出决定。这直接影响系统在不损害自身和整体功能性的情况下能够容忍的故障数量。需要容忍f
个故障的服务器数量(n)为n = 2 x f + 1
。
实际上,这意味着为了容忍一个故障,组内必须有三台服务器。因此,如果一台服务器故障,仍然有两台服务器形成多数(三个中的两个),使系统能够继续自动做出决策并进展。然而,如果第二台服务器非自愿故障,那么组(只剩下一台服务器)将阻塞,因为没有多数达成决定。
以下是一个小表格,说明了上述公式。
组大小 | 多数 | 即时容忍的故障数 |
1 | 1 | 0 |
2 | 2 | 0 |
3 | 2 | 1 |
4 | 3 | 1 |
5 | 3 | 2 |
6 | 4 | 2 |
7 | 4 | 3 |
原文:
dev.mysql.com/doc/refman/8.0/en/group-replication-observability.html
20.1.4.4 可观察性
尽管 Group Replication 插件中内置了许多自动化功能,但有时您可能需要了解幕后发生的情况。这就是 Group Replication 和 Performance Schema 的仪表化变得重要的地方。整个系统的状态(包括视图、冲突统计和服务状态)可以通过 Performance Schema 表进行查询。复制协议的分布式性质以及服务器实例之间达成一致并因此在事务和元数据上进行同步使得检查组的状态变得更加简单。例如,您可以连接到组中的单个服务器,并通过在与 Group Replication 相关的 Performance Schema 表上发出 select 语句来获取本地和全局信息。有关更多信息,请参见 第 20.4 节,“监控 Group Replication”。
,成员 A 怀疑成员 B 已经失败,但成员 B 并没有怀疑成员 A 已经失败 - 可能是由于路由或防火墙问题。一个成员也可以怀疑自己。一个与组其他成员隔离的成员怀疑所有其他成员已经失败。
如果一个怀疑持续超过 10 秒,怀疑的成员会试图向组内其他成员传播其观点,即怀疑的成员有缺陷。只有当怀疑的成员是通知者时才会这样做,这是从其内部 XCom 节点编号计算出来的。如果一个成员实际上与组的其他成员隔离开来,它可能会尝试传播其观点,但这不会产生任何后果,因为它无法获得其他成员的多数同意。只有当一个成员是通知者时,怀疑持续时间足够长以传播到组的其他成员,并且其他成员同意时,怀疑才会产生后果。在这种情况下,怀疑的成员被标记为从组中驱逐,在group_replication_member_expel_timeout
系统变量设置的等待期过后,驱逐机制检测到并实施驱逐后被驱逐。
在网络不稳定且成员经常在不同组合中失去和重新建立连接的情况下,理论上可能导致一个组标记所有成员进行驱逐,之后该组将停止存在并需要重新设置。为了应对这种可能性,从 MySQL 8.0.20 开始,Group Replication 的 Group Communication System (GCS)跟踪已被标记为驱逐的组成员,并在决定是否存在多数时将其视为被怀疑成员的组。这确保至少有一个成员留在组内,使组能够继续存在。当一个被驱逐的成员实际上已被从组中移除时,GCS 将删除其被标记为驱逐的记录,以便该成员可以重新加入组(如果有可能)。
有关可以配置的 Group Replication 系统变量的信息,以指定工作组成员对故障情况的响应以及被怀疑已经发生故障的组成员采取的行动,请参见 Section 20.7.7, “Responses to Failure Detection and Network Partitioning”。
原文:
dev.mysql.com/doc/refman/8.0/en/group-replication-fault-tolerance.html
20.1.4.3 容错性
MySQL Group Replication 基于 Paxos 分布式算法的实现,提供服务器之间的分布式协调。因此,它需要大多数服务器处于活动状态才能达成法定人数,从而做出决定。这直接影响系统在不损害自身和整体功能性的情况下能够容忍的故障数量。需要容忍f
个故障的服务器数量(n)为n = 2 x f + 1
。
实际上,这意味着为了容忍一个故障,组内必须有三台服务器。因此,如果一台服务器故障,仍然有两台服务器形成多数(三个中的两个),使系统能够继续自动做出决策并进展。然而,如果第二台服务器非自愿故障,那么组(只剩下一台服务器)将阻塞,因为没有多数达成决定。
以下是一个小表格,说明了上述公式。
组大小 | 多数 | 即时容忍的故障数 |
1 | 1 | 0 |
2 | 2 | 0 |
3 | 2 | 1 |
4 | 3 | 1 |
5 | 3 | 2 |
6 | 4 | 2 |
7 | 4 | 3 |
原文:
dev.mysql.com/doc/refman/8.0/en/group-replication-observability.html
20.1.4.4 可观察性
尽管 Group Replication 插件中内置了许多自动化功能,但有时您可能需要了解幕后发生的情况。这就是 Group Replication 和 Performance Schema 的仪表化变得重要的地方。整个系统的状态(包括视图、冲突统计和服务状态)可以通过 Performance Schema 表进行查询。复制协议的分布式性质以及服务器实例之间达成一致并因此在事务和元数据上进行同步使得检查组的状态变得更加简单。例如,您可以连接到组中的单个服务器,并通过在与 Group Replication 相关的 Performance Schema 表上发出 select 语句来获取本地和全局信息。有关更多信息,请参见 第 20.4 节,“监控 Group Replication”。