一、问题背景
我们的核心交易库采用"主机房 A + 备机房 B"跨机房主从架构:A 机房为主(读写),B 机房为从(只读报表/容灾),通过 MySQL 原生的主从复制(基于 binlog 的异步复制)跨机房同步。A、B 两机房之间走一条运营商 MPLS 专线(专线网关为 A 侧 10.0.0.1、B 侧 10.0.0.2,互联地址段 10.0.0.0/30),业务读写分离由中间件按"主写从读"路由。
2025 年 10 月 9 日上午,报表团队反馈 B 机房查到的数据与 A 机房对不上,随后复制监控告警。
二、故障现象
- 10:30 起,B 机房从库
Slave_IO_Running变为No,复制线程中断; Seconds_Behind_Master在中断前一度飙到 120s 以上,随后线程挂掉;- 业务侧读写分离出现数据不一致:用户在 A 机房刚下的单,在 B 机房报表里查不到;
- 从库错误日志反复出现连接主库超时、重试失败:
|
|
- 但 A 机房主库本身健康,本地读写无异常;B 机房到公网、到其他内网段正常,唯独到 A 机房专线时好时坏。
三、排查过程
第一步:确认是网络问题还是数据库问题。 在 B 机房从库机器上对主库 IP 做连续 ping 与 mtr:
|
|
平时该专线 RTT 在 3–5ms,此刻已到 1.8s 且 25% 丢包,明显是专线质量劣化。再看 mtr 路径:
|
|
抖动发生在跨机房 MPLS 这一段,而非本地。
第二步:确认抖动特征。 持续 5 分钟抓 RTT 分布,发现是周期性突发:每约 40 秒出现一次 1–2 秒的时延尖峰并伴随丢包,低谷期又恢复正常。这种"规律性抖动"典型是运营商侧 MPLS 链路做了某种重路由或存在微突发拥塞。
第三步:核对带宽与 QoS。 登录两侧专线网关查接口统计:
|
|
发现默认类有持续丢包,说明瞬时流量逼近 10G 带宽上限,突发时被丢弃——这也解释了复制线程在大数据事务(如批量报表回放)时被卡断。
第四步:关联变更。 联系运营商后确认,10:25 其对该 MPLS 链路做了一次保护倒换演练(未提前充分通知),部分流量被临时切到备用 LSP,路径变长、Buffer 不足,导致微突发丢包。
四、解决方案
- 先恢复复制:在 B 机房从库手动重启复制线程,并临时调大复制相关超时,避免瞬时抖动再次秒断:
|
|
- 数据库层加复制心跳,让中断更快被发现、连接更早重建:
|
|
- 网络层临时规避:与运营商确认保护倒换演练窗口,将其避开业务高峰;同时对关键复制流量打 MPLS EXP/QoS 高优先级标签,避免被默认类丢弃。
- 带宽扩容评估:将专线从 10G 临时升级保障,错峰跑批量报表,降低瞬时拥塞。
恢复后 Seconds_Behind_Master 从 120s 逐步回落到 0,数据一致性在约 15 分钟后追平。
五、根因分析
根因是跨机房 MPLS 专线出现周期性抖动+微突发丢包,击穿了异步复制链路的健壮性:
- 运营商保护倒换演练使部分流量临时走绕路 LSP,路径 RTT 从 3ms 涨到 1.8s,Buffer 不足引发丢包;
- MySQL 异步复制的 IO 线程对网络中断敏感,默认
net_read_timeout较短,丢包导致 binlog 拉取中断即报错退出; - 复制线程挂掉后,写入仍在 A 机房进行,B 机房数据持续滞后,读写分离架构下用户读到陈旧数据;
- 专线接口默认类 QoS 在带宽逼近上限时丢弃复制包,没有为数据库复制流量预留高优先级通道。
本质是跨机房强一致依赖(复制)跑在一条"无 QoS 保障、又会发生抖动"的单链路上,缺乏超时容错与流量分级。
六、预防措施
- 复制参数加固:从库设置合理的
MASTER_CONNECT_RETRY、net_read_timeout/net_write_timeout,并开启MASTER_HEARTBEAT_PERIOD,让抖动后能快速自愈而非长期挂死。 - 专线 QoS 分级:为数据库复制、存储同步等跨机房关键流量打高优先级 MPLS EXP 标签,保证其在拥塞时不被默认类丢弃。
- 双专线/多路径:关键机房间部署主备两条异构运营商专线,配合 BFD 快速检测 + 动态路由切换,单链路抖动自动切备用。
- 变更协同机制:要求运营商任何 MPLS 倒换、演练必须提前通知并避开业务高峰,纳入变更窗口管理。
- 一致性校验与告警:部署 pt-table-checksum 定期比对主从差异;对
Slave_IO_Running=No、Seconds_Behind_Master超阈值做秒级告警,避免滞后被业务先发现。 - 读写分离降级:当检测到从库延迟过大时,中间件自动把读请求切回主库,牺牲部分性能换取一致性。
七、总结
这次故障是典型的"网络抖动用数据一致性买单":一条 MPLS 专线的保护倒换演练,通过 MySQL 异步复制的脆弱连接,传导成了跨机房数据不一致。
排查路径很清晰——从库复制报错 → 网络层对照 ping/mtr 定位专线抖动 → 网关接口统计确认 QoS 丢包 → 关联运营商变更,一线工程师只要按顺序下钻就能锁定。更深的启示是:跨机房复制这类"看似数据库、实则强依赖网络"的链路,必须在网络侧做 QoS 分级、多路径容灾,在数据库侧做超时与心跳加固,双管齐下才能扛住底层链路的日常抖动。