作者简介:小明java问道之路,专心于研讨 Java/Liunx内核/C++及汇编/计算机底层原理/MySQL/中间件源码,就职于大型金融公司后端高级工程师,擅长交易范畴的高安全/可用/并发/性能的架构设计与演进、体系优化与稳定性建设。

热衷分享,喜爱原创~ 关注我会给你带来一些不一样的认知和成长

InfoQ签约作者、CSDN专家博主/后端范畴优质创作者/内容合伙人、阿里云专家/签约博主、51CTO专家

假如此文还不错的话,还请关注 、点赞 、保藏三连支撑一下博主~


本文导读

本文根据《MySQL仿制与高可用水平扩展架构实战》扩展其仿制的原理以及切换共同性问题。还没看根底的读者们请先行了解这篇根底的MySQL仿制详解与实战。本文主要对 MySQL 仿制原理与主备共同性同步作业原理解析。

一、MySQL 数据库仿制原理

本文根据《MySQL仿制与高可用水平扩展架构实战》扩展其仿制的原理以及切换共同性问题。还没看根底的读者们请先行了解这篇根底的MySQL仿制详解与实战。

1、根据句子的仿制

MySQL 5.0和更早版别只支撑根据句子的仿制,也称为逻辑仿制,这在数据库范畴很少见。

在根据句子的仿制形式中,主数据库记载导致数据更改的查询,当备用数据库读取并重放这些事情时,它实践上再次履行在主数据库上履行的SQL。

长处有许多,一是记载和履行这些句子能够坚持活动和备用同步;二是二进制日志中的事情更紧凑,因此相对而言,根据句子的形式不会运用太多带宽。更新TB数据的句子在二进制日志中只能占用几十个字节。

欠好的当地也有几点,一是主数据库上的数据更新或许取决于除履行句子之外的其他因素(例如时刻戳);二是存在着一些无法被正确仿制的 SQL(例如 MySQL中的CURRENT_USER()函数用于回来MySQL帐户的用户名和主机名,或者运用根据句子的仿制形式时,存储进程和触发器也或许存在问题);

三是更新有必要是串行化,这就需求更多的锁。

2、根据行的仿制

根据行仿制,该办法将实践数据记载在二进制日志中。

根据行仿制,能够正确仿制每一行,而且能够更有效地仿制某些句子,因为不需求重放更新数据库数据的查询操作,所以能够运用根据行的仿制形式来更有效地仿制数据,而且重放查询或许会很贵重。

-- 这时根据行的仿制就会仿制 SELECT 句子
INSERT INTO stable();
SELECT * FROM stable where id ='';

【MySQL】MySQL复制原理与主备一致性同步工作原理解析(原理篇)(MySQL专栏启动)

没有一种形式合适一切情况,一切MySQL能够在两种仿制形式之间动态切换。

默许情况下,运用根据句子的仿制形式,假如无法正确仿制句子,会主动切换到根据行的仿制形式。

MySQL 还能够将会话等级变量设置为 binlog_format(二进制格局),以控制二进制日志格局。

关于根据行的仿制,时刻点康复很困难,但并非不或许。稍后第二节讲到日志服务器将有所协助。

3、两种仿制方法的比较与生产环境运用

在实践生产环境咱们一般会运用根据行的仿制,因为这种办法能够比较读多写少许多无效的sql,

可是假如数据库版别太低,就只有根据sql的仿制方法。

3.1、根据sql的仿制优缺陷

长处:

1、当主备形式不同时逻辑仿制能够在各种条件下作业,根据句子的仿制更灵敏。

2、根据句子的仿制进程基本上是履行SQL句子,以易于理解的方法在跑步进程中产生的变化,当出现问题时,能够很好地定位

缺陷:

MySQL一些情况下无法仿制根据句子的形式。存储进程、触发器存在一些仿制的过错。简略地说:假如有运用触发器或存储进程,不能运用根据句子的仿制形式。

3.2、根据行的仿制形式的优缺陷

长处:

1、根据行的仿制形式无法处理的场景几乎没有(包含SQL结构、触发器、存储进程等都能够履行)。

2、能够削减锁的运用,因为它不要求这串行化是可重复的

3、根据行的仿制形式只会记载数据更改,因此二进制日志中记载的实践上是主数据库上已更改的数据。

此形式能够更清楚地知道服务器上产生了什么更改,并更好地记载数据更改。根据行的二进制日志还记载更改之前的数据,有利于某些数据康复。

缺陷:

因为履行过的 sql 句子未记载在日志中,因此无法确认履行了哪些SQL句子,只知道数据行中的更改。

二、MySQL 主备共同性原理

1、 主/备切换进程

在的主/备切换进程,图1中,客户端读取和写入都直接访问 DB1,而 DB2 是 DB1 的备用数据库,而且仅同步 DB1 的更新并在本地履行它们,这样, DB2 和DB1 的数据能够坚持相同。虽然 DB2 未被直接访问,但我依然主张您将 DB2 设置为只读形式

当需求切换时,将切换到图2。此刻,客户端将读取和写入节点 DB2,而 DB1 是 DB2 的备用数据库。

【MySQL】MySQL复制原理与主备一致性同步工作原理解析(原理篇)(MySQL专栏启动)

2、MySQL 的sql句子同步内部作业原理

在从客户端接收到更新恳求后,主库履行内部事务的更新逻辑并写入undo log、bin log、redo log。

备库和主库之间坚持长衔接,主数据库A内有一个线程 dump_thread,用于服务备库的长衔接。

【MySQL】MySQL复制原理与主备一致性同步工作原理解析(原理篇)(MySQL专栏启动)

详细流程如下,在备用数据库上,运用 change-master (更改主机)指令设置主数据库 的IP、端口、用户名和密码,以及恳求bin log的方位(此方位包含文件名和日志偏移量)。

在备用数据库上履行 start slave (发动从属设备)指令。此刻,备用数据库将发动两个线程,即figure_Thread(图形线程)和sql_Thread(sql线程)中显示的 io 其中 io_Thread 负责与主库建立衔接。

主库校验完用户名、密码后,开始按照备库传过来的方位,从本地读取 bin log,发给从库。

获取 bin log后,备用数据库将其写入本地文件,该文件称为 relay log (中继日志)。sql_Thread 读取传输日志,解析日志中的指令并履行。

3、MySQL 循环仿制问题

双主结构(MM形式)中,客户端在 主库A 上更新了一条句子,然后再把生成的 bin log 发送到主库 B,节点 B 履行完这条更新句子后也会生成 bin log。这时主库 A,不知道这是 B库的同步当成新的履行操作就会产生循环仿制问题。

如何解决呢?

首要设置两个数据库的服务器ID不同。假如相同,则不能设置为主/备用联系;

当备用数据库接收到 bin log 并重放它时,它会生成一个新的 bin log,其服务器ID与原始binlog相同;

每个数据库收到自己主数据库发送的日志后,首要判别服务器ID。假如与自己的ID相同,则表示bin log 日志是自己生成的,将直接丢弃。

总结

本文根据《MySQL仿制与高可用水平扩展架构实战》扩展其仿制的原理以及切换共同性问题。还没看根底的读者们请先行了解这篇根底的MySQL仿制详解与实战。本文主要对 MySQL 仿制原理与主备共同性同步作业原理解析。

本文正在参加「技能专题19期 漫谈数据库技能」活动