mysql保证高可用的根本就在于减少HA备份的延迟时间
导致主备延迟时间过长的几个原因:
- 首先,有些部署条件下,备库所在机器的性能要比主库所在的机器性能差
- 备库的压力大
- 大事务(DDL,我觉得DDL也相当于一个大事务)
- 大表 DDL
- 主库DML语句并发大,从库qps高
- 从库服务器配置差或者一台服务器上几台从库(资源竞争激烈,特别是io)
- 主库和从库的参数配置不一样
- 从库上在进行备份操作
- 表上无主键的情况(主库利用索引更改数据,备库回放只能用全表扫描,这种情况可以调整slave_rows_search_algorithms参数适当优化下)
- 设置的是延迟备库
- 备库空间不足的情况下
由于主备延迟的存在,所以在主备切换的时候,就相应的有不同的策略
- 可靠性优先策略
判断备库 B 现在的 seconds_behind_master,如果小于某个值(比如 5 秒)继续下一步,否则持续重试这一步;
把主库 A 改成只读状态,即把 readonly 设置为 true;
判断备库 B 的 seconds_behind_master 的值,直到这个值变成 0 为止;
把备库 B 改成可读写状态,也就是把 readonly 设置为 false;
把业务请求切到备库 B。
- 可用性优先策略
mysql> CREATE TABLE `t` (
`id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`c` int(11) unsigned DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB;
insert into t(c) values(1),(2),(3);
这个表定义了一个自增主键 id,初始化数据后,主库和备库上都是 3 行数据。接下来,业务人员要继续在表 t上执行两条插入语句的命令,依次是:
insert into t(c) values(4);
insert into t(c) values(5);
假设,现在主库上其他的数据表有大量的更新,导致主备延迟达到5 秒。在插入一条 c=4 的语句后,发起了主备切换。