必须同时调整slave_net_timeout和master_connect_retry:前者控制空闲断连时机(如设30秒),后者决定断连后重试间隔(如设10秒),单独调整任一参数均无法解决io线程卡connecting或反复断连问题。

直接改 slave_net_timeout 和 MASTER_CONNECT_RETRY,别只调一个。
为什么 IO 线程卡在 Connecting 或反复断连
根本不是“连不上等太久”,而是“连上了但空闲着,突然被踢掉,再傻等 60 秒才重试”。slave_net_timeout 默认是 3600 秒(1 小时),只要主库 1 小时没发 binlog,IO 线程就主动断开连接;断开后,才轮到 MASTER_CONNECT_RETRY 控制下一次重试要等几秒——而它的默认值是 60 秒。结果就是:抖动 30 秒 → 断连 → 立即重试失败 → 等 60 秒 → 再试 → 又失败 → 再等 60 秒……实际恢复可能拖到 2~3 分钟。
常见现象包括:Slave_IO_Running: Connecting 持续几十秒、Last_IO_Error 出现 “error connecting to master” 但主库明明在线、Seconds_Behind_Master 突然跳涨。
怎么配才真正生效(局域网典型场景)
必须同时调整两个参数,并确保它们逻辑对齐:
-
slave_net_timeout = 30:让 IO 线程在空闲 30 秒后主动断开,及时响应网络抖动 -
MASTER_CONNECT_RETRY = 10:断开后 10 秒内立刻重试,避免长等待 - 配套执行
SET GLOBAL relay_log_recovery = ON:防止重连后 relay log 位置错乱(MySQL 5.7+ 必须开)
修改后需重启复制生效:STOP SLAVE; START SLAVE;。不要只改配置文件,记得用 SET GLOBAL 在线生效(否则下次重启前不生效)。
跨可用区或云厂商间怎么调
RTT 更高、网络毛刺更多,不能简单照搬 30/10:
- RTT 在 20–80ms(如阿里云华东1→华北2):
slave_net_timeout = 60,MASTER_CONNECT_RETRY = 30 - 若主库偶发大事务(比如批量 delete 超过 30 秒无 binlog 输出),必须同步调高
slave_net_timeout,否则它会误判为空闲超时而主动断连 - MySQL 8.0.22+ 可用更明确的语法:
SOURCE_CONNECTION_AUTO_RETRY = 1+SOURCE_RETRY_COUNT = 3,但前提是 GTID 已开启且relay_log_recovery = ON
最容易被忽略的坑
很多人只改了 MASTER_CONNECT_RETRY,却忘了 slave_net_timeout 才是真正触发断连的开关。单独调小它没用,单独调大它反而让故障暴露更慢。另外,MASTER_RETRY_COUNT(或 8.0.22+ 的 SOURCE_RETRY_COUNT)控制的是“连续失败几次后彻底放弃”,默认是 0(无限重试),生产环境建议设为 3~5,避免无限循环失败掩盖真实问题。











