mysql主从同步作用及设置_2018_lcf

生产环境中常用的一种数据库备方式,适用于组建热备及高可用

用途和用条件 

mysql主从复制用途
  • 实时灾备,用于故障切换
  • 读写分离,提供查询服务
  • 备份,避免影响业务
 
主从部署必要条件:
  • 主库开启binlog日志(设置log-bin参数)
  • 主从server-id不同
  • 从库服务器能连通主库

//注:关闭selinux ,firewall

主从原理

mysql主从复制原理
mysql主从同步作用及设置_2018_lcf 

 

从库生成两个线程,一个I/O线程,一个SQL线程;
 
i/o线程去请求主库 的binlog,并将得到的binlog日志写到relay log(中继日志) 文件中;
主库会生成一个 log dump 线程,用来给从库 i/o线程传binlog;
 在没开启log_slave_updates时, Replay log的记录操作不会写进binlog里.
SQL 线程,会读取relay log文件中的日志,并解析成具体操作,来实现主从的操作一致,而最终数据一致;

同步模式

异步复制(Asynchronous replication)
主库在执行完客户端提交的事务后会立即将结果返给客户端,并不关心从库是否已经接收并处理。

全同步复制(Fully synchronous replication)
当主库执行完一个事务,所有的从库都执行了该事务才返回给客户端。

半同步复制(Semisynchronous replication)
介于异步复制和全同步复制之间,主库在执行完客户端提交的事务后不是立刻返回给客户端,而是等待至少一个从库接收到并写到relay log中才返回给客户端。

主从常见架构

-- 基本应用
单向复制:主 --> 从

-- 扩展应用
链式复制:主 --> 从 --> 从
双向复制:主 <--> 从

放射式复制:从 <-- 主 --> 从


1) 单向复制 主-->从 实现方式

A) 主库配置步骤:
--1--启用binlog 修改配置文件/etc/my.cnf
[[email protected]~]# vim /etc/my.cnf
[mysqld]
server_id=66 // 数字编号可以自宝义
log-bin=/logdir/plj //开启外放目录, 方便管理 ,plj可以换成有意义有名字
binlog_format="mixed" //有三种式,用这种比较多,下面有说明
#log_slave_updates //用于主从从模式下, 中间那个从开启这个功能, 使其中继日志操作也能写进binlog里
#relay_log=dbsvr2-relay-bin   //指定中继日志文件名,dbsvr2自定义名
#replicate_do_do=mysql   //仅同步的库
#replicate_ignore_db=mysql ,web   //不同步的库, 和上面replicate_do_do选择一种开放定义
[[email protected] ~]#systemctl restart mysqld

mysql复制主要有三种方式:基于SQL语句的复制(statement-based replication, SBR),基于行的复制(row-based replication, RBR),混合模式复制(mixed-based replication, MBR)。对应的,binlog的格式也有三种:STATEMENT,ROW,MIXED。

① STATEMENT模式(SBR)

每一条会修改数据的sql语句会记录到binlog中。优点是并不需要记录每一条sql语句和每一行的数据变化,减少了binlog日志量,节约IO,提高性能。缺点是在某些情况下会导致master-slave中的数据不一致(如sleep()函数, last_insert_id(),以及user-defined functions(udf)等会出现问题)

② ROW模式(RBR)

不记录每条sql语句的上下文信息,仅需记录哪条数据被修改了,修改成什么样了。而且不会出现某些特定情况下的存储过程、或function、或trigger的调用和触发无法被正确复制的问题。缺点是会产生大量的日志,尤其是alter table的时候会让日志暴涨。

③ MIXED模式(MBR)

以上两种模式的混合使用,一般的复制使用STATEMENT模式保存binlog,对于STATEMENT模式无法复制的操作使用ROW模式保存binlog,MySQL会根据执行的SQL语句选择日志保存方式


--2--做用户授权(添加一个从同步数据时的连接用户)

[[email protected]~]#mysql -uroot -p123456
mysql> grant replication slave on *.*
-> to
-> [email protected]"192.168.4.53" //创建账号,和指定登陆IP,可用'%'代替
-> identified by "123456";  //设置密码
mysql>show master staatus;
+---------------+----------+--------------+------------------+-------------------+
| File          | Position | Binlog_Do_DB | Binlog_Ignore_DB | Executed_Gtid_Set |
+---------------+----------+--------------+------------------+-------------------+
| master.000156 |     478 |            |                  |                   |
+---------------+----------+--------------+------------------+-------------------+
1 row in set (0.00 sec)
//查看正在使用的binlog日志文件信息 show master staatus;
//主要查看正File项和Position项信息;
B) 从库配置步骤
--1--指定server-id 
[[email protected]~]# vim /etc/my.cnf
[mysqld]
server_id=68
--2--管理员登陆指定主数据库服务器的信息
mysql> change master to
-> master_host="192.168.4.52",    //主库IP
-> master_user="yaya",        //连主库用户
-> master_password="123456",    //用户密码
-> master_log_file="host52-bin.000002",  //binlog日志文件名
-> master_log_pos=154;        //偏移量
1 row in set (0.00 sec)
--3--启动slave进程
mysql> start slave;
mysql> show slave status\G;
...
Slave_IO_Running: YES
Slave_SQL_Running: YES
....
//如果那两项都是yes就表示设置成功了, 这时主库有数据更新添加等操作时,从库也会跟着同步操作
   //注: reset slave;清空设置  stop slave; 停止从库同步命令
   
2) 链式复制 主1 --> 从2 --> 从3 实现方式

-- 这里主1和从2如上面主-从操作那样先设置成功

-- 然后再从2和从3如上面主-从操作那样设置成功(从2是从3的主库)

-- 再把从2#log_slave_updates 这一条注释去掉就可以了

3)双向复制:主 <--> 从(互为主从) 实现方式
- 把1)的操作相互设置下即可,也就是互相互授权一个slave账号,都开启bin-log和slave功能

4)放射式复制:从 <-- 主 --> 从实现方式
- 设置一台主库,再设置几个授权账号即可,从库按1)里的从库设置即可

5 )同步模式设置

先查看是否允许动态加载模块 默认允许

mysql> show variables like "have_%";

....

have_dynamic_loading   | YES    //默认是允许

...

-->命令行加载插件(需要mysql的root权限装载)
主库: mysql> install plugin rpl_semi_sync_master soname 'semisync_master.so';
Query OK, 0 rows affected (0.11 sec)

从库: mysql> install plugin rpl_semi_sync_slave soname 'semisync_slave.so';
Query OK, 0 rows affected (0.11 sec)

查看: mysql> select plugin_name,plugin_status from information_schema.plugins where plugin_name like '%semi%';
+----------------------+---------------+
| plugin_name | plugin_status |
+----------------------+---------------+
| rpl_semi_sync_master | ACTIVE |
+----------------------+---------------+
1 row in set (0.01 sec)

-->启用半同步复制(临时设置,重启后失效)
在安装完插件后,半同步复制默认是关闭的
主库:mysql> SET GLOBAL rpl_semi_sync_master_enabled = 1;   //1表示开启
从库:mysql> SET GLOBAL rpl_semi_sync_slave_enabled = 1;
查看: mysql> show variables like "rpl_semi_sync_%_enabled";

-->设置永久启用,修改/etc/my.cnf配置文件,修改后需要重启服务


写在主配置文件/etc/my.cnf 的[mysqld]下方(下面是主从模式)
主库:
plugin-load="rpl_semi_sync_master=semisync_master.so"
rpl_semi_sync_master_enabled=1

从库:
plugin-load=rpl_semi_sync_slave=semisync_slave.so
rpl_semi_sync_slave_enabled=1

双向复制:主 <--> 从(互为主从,两边都加入下面配置)
[mysql]
plugin-load="rpl_semi_sync_master=semisync_master.so;rpl_semi_sync_slave=semisync_slave.so"
rpl-semi-sync-slave-enabled = 1

rpl-semi-sync-master-enabled = 1

//在有的高可用架构下,多是用双向复制:主 <--> 从(互为主从),这时master和slave机都开启这个功能即可




常问题及解决方法

 从库设置问题
  • -->常见的有uuid相同, 主要是由全复制数据库时产生
  • [[email protected] ~]# vim /var/lib/mysql/auto.cnf 
    [auto]
    server-uuid=4506f68e-63d2-11e8-a510-525400e1b4fc  //修改其中一个以上数字即可,然后重启服务
  • -->server-id问题
  • [[email protected]~]# vim /etc/my.cnf
    [mysqld]
    server_id=66 //主要是这个值冲突,修改下就可以了,不能和其它服务器id相同
  • -->Slave_IO_Running: NO /connecting
  • 这个主要是主库授权时IP写错, 或从库设置时写错IP, 用户名等, 

mysql主从复制存在的问题:

  • 主库宕机后,数据可能丢失
  • 从库只有一个sql Thread,主库写压力大,复制很可能延时
 
解决方法:
  • 半同步复制---解决数据丢失的问题
  • 并行复制----解决从库复制延迟的问题