能换,但必须先确认从库已完全应用完所有中继日志,否则必然丢数据;需验证Slave_IO_Running=No、Slave_SQL_Running=Yes、SHOW PROCESSLIST显示“Has read all relay log”,再比对Relay_Master_Log_File与Exec_Master_Log_Pos确认执行位点。

能换,但必须先确认从库已完全应用完所有中继日志,否则必然丢数据。
如何判断从库是否真的“追平”了原主库
很多人只看 Seconds_Behind_Master = 0 就动手,这是最常见误操作起点。这个值在主库宕机后会变成 NULL 或停滞不更新,完全不可信。
真正可靠的判断依据是:
-
Slave_IO_Running: No(说明已连不上原主库,IO线程停了) -
Slave_SQL_Running: Yes(SQL线程还在跑) - 执行
SHOW PROCESSLIST,看到 SQL 线程的State是Has read all relay log; waiting for more updates - 再查
Relay_Master_Log_File和Exec_Master_Log_Pos,这两个值代表它最后执行到原主库哪条 binlog,后续切换时其他节点要用
STOP SLAVE 和 RESET SLAVE ALL 的区别与风险
STOP SLAVE 只暂停复制线程,master.info 和 relay-log.info 文件都还留着;而 RESET SLAVE ALL 会彻底删掉这两个文件,清空所有复制元数据。
所以:
- 计划内切换且原主库确定不再回归 → 用
RESET SLAVE ALL - 只是临时断开、后续可能切回 → 用
STOP SLAVE+ 手动记录SHOW SLAVE STATUS\G输出,避免信息丢失 - 如果复制参数写死在
my.cnf里(比如master-host=...),RESET SLAVE ALL后重启 MySQL 仍会读配置自动重连,导致意外恢复旧关系 —— 这就是为什么官方强烈建议不要把复制配置放配置文件里
CHANGE MASTER TO 指向新主库时最关键的三个参数
其他参数可以省略,但这三个必须显式指定,否则容易连错位置或跳过事务:
-
MASTER_LOG_FILE = 'mysql-bin.000012':必须填新主库上SHOW MASTER STATUS返回的File值,不是从旧状态里抄的 -
MASTER_LOG_POS = 154:对应上面File的起始偏移,通常为154(MySQL 8.0+ 默认),但不能假设,得实查 -
MASTER_AUTO_POSITION = 0:如果没开 GTID,必须显式关掉,否则CHANGE MASTER TO会忽略MASTER_LOG_FILE和MASTER_LOG_POS,直接报错
示例命令:
CHANGE MASTER TO MASTER_HOST='192.168.1.20', MASTER_USER='repl', MASTER_PASSWORD='repl_pass', MASTER_LOG_FILE='mysql-bin.000003', MASTER_LOG_POS=154, MASTER_AUTO_POSITION=0;
read_only 和 super_read_only 必须手动关闭才能写入
很多从库默认开了 read_only=1,但提升为主库后,不关它就无法接受任何写请求,应用连上去会直接报错 ERROR 1290 (HY000): The MySQL server is running with the --read-only option so it cannot execute this statement。
注意两点:
-
SET GLOBAL read_only = OFF只影响普通用户,对拥有SUPER权限的账号无效 - 如果启用了
super_read_only(MySQL 5.7.20+),它优先级更高,必须同时执行SET GLOBAL super_read_only = OFF,否则read_only关了也没用 - 这两项设置不会持久化,MySQL 重启后恢复原值,如需长期生效,得改配置文件并重启
整个切换过程里最容易被忽略的是:新主库的 server-id 必须和集群里其他节点不同,且不能为 0 或 1(尤其当原主库 server-id=1 且未清理干净时)。一旦重复,其他从库可能收不到事件,或者自己又把自己当成从库同步回来,造成环形复制。


















