作者:赵拂晓
爱可生 MySQL DBA 团队成员,Oracle 10g OCM,MySQL 5.7 OCP,善于数据库性能问题诊断、事务与锁问题的剖析等,负责解决客户 MySQL 及我司自研 DMP 平台日常运维中的问题,对开源数据库相干技术十分感兴趣。
本文起源:原创投稿
* 爱可生开源社区出品,原创内容未经受权不得随便应用,转载请分割小编并注明起源。
背景
该问题来自某客户,据形容,他们在部署 MySQL 主从复制时,有时候仅在主库上创立复制用户,有时候主从实例上都会去别离创立复制用户,发现这两种形式都能够胜利建设复制。针对这一景象,进行了一轮验证,来察看采纳不同形式创立复制用户对主从复制的影响。
通常来说,用得较多的形式是在搭建主从复制前,先在主库创立好复制用户,而后做一个 Xtrabackup 物理全备,再拿到从库上复原并搭建主从。除此以外,还有哪些形式呢?别离对主从复制有哪些影响?一起来看一下。
验证
- MySQL 版本为 5.7.32,主库:10.186.60.62,从库:10.186.60.68。
- 为了演示不便,本次搭建主从复制时均采纳 mysqldump 进行逻辑备份。
场景 1:仅在主库创立复制用户
1. 主库做一个备份并拷贝到从库
/usr/local/mysql5732/bin/mysqldump --single-transaction --master-data=2 -B zlm -S /tmp/mysql3332.sock -p > zlm.sql
scp zlm.sql root@10.186.60.68:~
2. 登陆从库执行导入
mysql> source zlm.sql
因为没有应用参数 –set-gtid-purged=off,导出的语句中会带有 SET @@GLOBAL.GTID_PURGED=’xxxx:1-xx’ 并执行,导入前须要先在从库上执行 reset master。
3. 主库创立复制用户
mysql> create user repl1 identified by 'repl1';
4. 从库配置主从复制并启动
mysql> change master to master_host='10.186.60.62',master_port=3332,master_user='repl1',master_password='repl1',master_auto_position=1;
mysql> start slave;
启动复制后,报了 Error 1045 的谬误,此处并不是明码错,而是没有给复制用户配置 replication slave 权限,在主库上对 repl1 用户执行赋权后(grant replication slave on *.* to repl1;),再启动复制就失常了。
主从复制失常当前,也会在从库上创立复制用户 repl1。
从库上并没有创立过复制用户 repl1,主从复制就失常搭建好了,为什么呢?因为 change master to 语句中指定的 master_user 是主库上的复制用户,从库通过这个用户连贯到主库进行同步,当开启复制线程后,主库上创立复制用户的语句会在从库上进行回放,于是从库上也会有这个复制用户了。
论断 1
- 搭建主从复制时,在从库创立复制用户不是必须的,仅在主库创立即可,复制用户会同步到从库。
场景 2:主从库独自创立复制用户(create 语句)
1. 主库做一个备份并拷贝到从库(gtid_purged=xxxx:1-23)
2. 从库执行导入
3. 主库创立复制用户并赋权
mysql> create user repl2 identified by 'repl2';
mysql> grant replication slave on *.* to repl2;
4. 从库创立复制用户
因为不想在从库上产生由从库 uuid 写入的 binlog 事务,此处设置了 sql_log_bin=0,使事务不被记录到 binlog 中,起因是在数据库治理平台对高可用集群进行治理时,通常是不容许从库上有主库不存在的 GTID 事务的。
5. 从库配置主从复制并启动
mysql> change master to master_host='10.186.60.62',master_port=3332,master_user='repl2',master_password='repl2',master_auto_position=1;
mysql> start slave;
因为从库上曾经创立了复制用户,当回放到主库的这个事务时会报 Error 1396 的谬误。
能够用 create user 语句创立一个反复用户来验证。
解析主库 binlog,启动复制后执行的第一个事务就是这个 24 的创立用户语句。
论断 2
- 在从库导入备份后并别离在主、从库独自创立复制用户后,当从库执行到创立用户的事务时会导致复制中断。
场景 3:主从库独自创立复制用户(grant 语句)
1. 主库做一个备份并拷贝到从库(gtid_purged=xxxx:1-28)
2. 从库执行导入
3. 主库创立复制用户
mysql> grant replication slave on *.* repl3 identified by 'repl3';
4. 从库创立复制用户
5. 从库配置主从复制并启动
mysql> change master to master_host='10.186.60.62',master_port=3332,master_user='repl2',master_password='repl2',master_auto_position=1;
mysql> start slave;
这次启动复制后并没有报错。为何用 grant 语句创立用户就能够,用 create 语句就不行呢?
create 与 grant 语句都会产生事务并记录到 binlog 中,但区别是 grant 语句是一个近似幂等的操作,而 create 语句不是。
解析主库 binlog,29 和 30 都是反复执行 grant 的事务。
察看 show slave stauts\G,从库上也把 29,30 这两个事务都回放掉了,反复执行它们并不影响主从复制。
但要留神的是,在 MySQL 8.0 中曾经禁止通过 grant 这种语法来创立用户了。
论断 3
- 从库导入备份并在主从库别离应用 grant 语句创立用户后,在从库回放时不会导致复制中断。
总结
1. 依据以上验证后果得悉,在搭建主从复制时,采纳多种形式创立复制用户都是可行的,但有些形式存在一些限度,如:在主、从实例上别离创立复制用户。尽管执行 grant 语句创立用户不会导致复制中断,但其并不是规范的 MySQL 创立用户语法,在 MySQL 8.0 中已被视为语法错误,因而不举荐采纳这样的形式来搭建主从。
2. 创立复制用户的形式
Create 语句创立用户时
1. 主库创立完复制用户后做备份,再配置主从
2. 备份后仅在主库创立复制用户,再配置主从(举荐)
3. 如果要在主、从库别离创立复制用户,应先设置 session 级别的 sql_log_bin=0,再配置主从
Grant 语句创立用户时(MySQL 5.7 及以下版本)
1. 主库先创立复制用户后备份,再配置主从
2. 仅在主库创立复制用户,再配置主从(举荐)
3. 主、从库别离创立复制用户,再配置主从