根本原因是SQL线程单线程回放relay log,主库多线程并发写入而从库强制串行执行,中间任一慢查询、锁等待或大事务都会阻塞后续全部操作,导致延迟陡增。

为什么MySQL从库单线程回放会导致性能瓶颈
根本原因不是“线程少”,而是主库并发写入与从库串行执行之间存在不可调和的时序矛盾:主库能同时处理数百个事务,而从库 SQL Thread 只能一条接一条地重放 relay log 里的事件,中间还夹杂锁等待、磁盘刷盘、大事务阻塞等放大效应。
SQL Thread 卡在 “executing” 状态就是典型信号
当你执行 SHOW PROCESSLIST,看到从库 SQL Thread 长时间停留在 executing + 某条 UPDATE/ALTER/DROP 语句,说明它正被一个耗时操作死死拖住。后续所有事务都得排队——这不是慢,是“堵”。
- 大事务(比如未分批的 DELETE FROM orders WHERE create_time
- DDL 操作(
ALTER TABLE)默认不可并行,一旦出现,后面所有事务强制串行化 - 无主键表的 DML 在 ROW 格式下无法生成唯一写集,WRITESET 并行直接失效
- 从库
innodb_flush_log_at_trx_commit=1+sync_binlog=1会让每条事务都刷盘,I/O 成为硬瓶颈
为什么设了 slave_parallel_workers=4 却还是单线程
参数开了 ≠ 真的并行。MySQL 8.0 的 WRITESET 或 LOGICAL_CLOCK 并行复制,是一套强依赖链路,漏掉任意一环就自动 fallback 到单线程:
MySQL 数据库管理技能,能够通过自然语言查询和管理数据库,支持 SELECT/INSERT/UPDATE/DELETE、表管理、备份恢复等操作。当用户提及 MySQL、数据库查询、建表或数据备份时使用此技能。
- 主库
binlog_format不是ROW→ 写集无法提取 → 并行失效 - 主库
binlog_transaction_dependency_tracking不是WRITESET(或COMMIT_ORDER)→ 从库 coordinator 拿不到分组依据 - 从库
slave_preserve_commit_order=ON(MySQL 8.0 默认)→ 强制 worker 等待前序事务提交完成,实际串行 - 从库
slave_parallel_type仍为DATABASE(旧配置残留)→ 跨库事务直接退化
SHOW SLAVE STATUS\G 里真正暴露单线程真相的字段
别只盯着 Seconds_Behind_Master。这几个字段才是关键证据:
-
Slave_SQL_Running_State显示Reading event from the relay log:协调器(coordinator)没分发任务,说明并行调度链路断了 -
Relay_Log_Space持续上涨,但Exec_Master_Log_Pos几乎不动:中继日志疯狂堆积,SQL Thread 堵死 -
Retrieved_Gtid_Set和Executed_Gtid_Set差距大,Seconds_Behind_Master却不涨:事务已拉到本地,但因依赖检测失败或写集为空,被 coordinator 强制串行
并行复制不是“调个参数就提速”,它是主库日志生成逻辑、从库解析策略、事务结构特征三者严丝合缝咬合的结果。任何一个环节松动,就会无声无息退回单线程——而你可能还在查网络延迟。


















