分析&回答
主从复制原理
-
主库记录binlog日志 在每次准备提交事务完成数据更新前,主库将数据更新的事件记录到二进制日志binlog中。主库上的sync_binlog参数控制binlog日志刷新到磁盘。
-
从库IO线程将主库的binlog日志复制到其本地的中继日志relay log中 从库会启动一个IO线程,IO线程会跟主库建立连接,然后主库会启动一个特殊的二进制转储线程(binlog dump),二进制转储线程会读取主库上binlog中的事件,它不会一直对事件进行轮询,当它追赶上了主库就会进入睡眠状态,直到主库发送信号量通知其有新事件产生才会被唤醒。
-
从库的SQL线程进行重放 从库的SQL线程从中继日志relay log中读取事件并在从库执行,从而实现从库数据的更新。
注意:主库上并发的修改操作在从库上只能串行化执行,因为只有一个SQL线程来重放中继日志,这也是很多工作负载的性能瓶颈所在。虽然有一些针对该问题的解决方案,但大多数用户仍然受制于单线程。在老版本的MySQL中,IO线程是单线程的,但新版本IO线程也可以是多线程的,但无论怎样,SQL线程是单线程的。
主从复制方法
并行复制(multi-threaded slave)
MySQL在5.6版本中使用并行复制来解决主从延迟问题。所谓并行复制,指的就是从库开启多个SQL线程,并行读取relay log中不同库的日志,然后并行重放不同库的日志,这是库级别的并行。
- MySQL5.6中的并行复制
MySQL5.6的并行复制只是基于schema的,也就是基于库的。当有多个库时,多个库可以并行进行复制,库与库之间互不干扰。但多数情况下,可能只是单schema,即只有单个库,那基于schema的复制就没什么用了。
其核心思想是:不同schema下的表并发提交时的数据不会相互影响,即slave节点可以用对relay log中不同的schema各分配一个类似SQL功能的线程,来重放relay log中主库已经提交的事务,保持数据与主库一致。
只需设置参数slave_parallel_workers即可开启并行复制,例如设置 slave_parallel_workers= 4,即有4个SQL Thread(coordinator线程)来进行并行复制。
- MySQL5.7中的并行复制
MySQL 5.7对并行复制做了进一步改进,开始支持真正的并行复制功能。MySQL5.7的并行复制是基于组提交的并行复制,官方称为enhanced multi-threaded slave(简称MTS),延迟问题已经得到了极大的改善。
其核心思想是:一个组提交的事务都是可以并行回放(配合binary log group commit);slave机器的relay log中 last_committed相同的事务(sequence_num不同)可以并发执行。
通过设置参数slave_parallel_workers并且global.slave_parallel_type=‘LOGICAL_CLOCK’,即可支持一个schema下,slave_parallel_workers个的worker线程并发执行relay log中主库提交的事务。
半同步复制(Semisynchronous Replication)
- 5.5集成到mysql,以插件的形式存在,需要单独安装
- 确保事务提交后binlog至少传输到一个从库
- 不保证从库应用完这个事务的binlog
- 性能有一定的降低,响应时间会更长
- 网络异常或从库宕机,卡主主库,直到超时或从库恢复
半同步复制原理
- 事务在主库写完binlog后需要从库返回一个已接受,才放回给客户端;
- 5.5集成到mysql,以插件的形式存在,需要单独安装
- 确保事务提交后binlog至少传输到一个从库
- 不保证从库应用完成这个事务的binlog
- 性能有一定的降低
- 网络异常或从库宕机,卡主库,直到超时或从库恢复
多源复制(Multi-Source Replication)
MySQL 5.7之前只能实现一主一从、一主多从或者多主多从的复制。如果想实现多主一从的复制,只能使用 MariaDB,但是 MariaDB 又与官方的 MySQL 版本不兼容。
MySQL 5.7 开始支持了多主一从的复制方式,也就是多源复制。所以,多源复制至少需要两个Master和一个Slave。
多源复制使用场景
- 数据分析部门会需要各个业务部门的部分数据做数据分析,这个时候就可以用到多源复制把各个主数据库的数据复制到统一的数据库中。
- 在从服务器进行数据汇总,如果我们的主服务器进行了分库分表的操作,为了实现后期的一些数据统计功能,往往需要把数据汇总在一起再统计。
- 在从服务器对所有主服务器的数据进行备份,在MySQL 5.7之前每一个主服务器都需要一个从服务器,这样很容易造成资源浪费,同时也加大了DBA的维护成本,但MySQL 5.7引入多源复制,可以把多个主服务器的数据同步到一个从服务器进行备份。
MySQL常见的两个问题:
-
主从延迟问题 主从延迟问题,是由于从库仅使用单个SQL线程进行回放,速度跟不上主库。所以MySQL使用并行复制来进行改进,MySQL5.6的并行复制是基于schema的,MySQL5.7的并行复制是基于组提交的。
-
异步复制导致数据丢失问题 数据丢失问题,是由于MySQL是异步复制的,主库上的事务提交并不关心从库是否复制成功,就可能导致数据丢失。可以使用MySQL的半同步来解决这个问题,即主库保证至少有一个从库复制成功才会返回。半同步复制功能以插件形式提供,需要手动开启。
反思&扩展
主从复制的方式
主从复制用途
- 实时灾备,用于故障切换
- 读写分离,提供查询服务
- 备份,避免影响业务
喵呜面试助手:一站式解决面试问题,你可以搜索微信小程序 [喵呜面试助手] 或关注 [喵呜刷题] -> 面试助手 免费刷题。如有好的面试知识或技巧期待您的共享!