是磁盘IO瓶颈,需结合SHOW PROCESSLIST、iostat及配置排查;迁移日志表应创建专用表空间并ALTER TABLE指定,注意版本、锁表与权限;innodb_log_group_home_dir与业务表存储无关;SSD仍卡可能因挂载参数、O_DIRECT未启用或表结构不合理。

日志表写入慢,INSERT 延迟高,是不是磁盘 IO 问题?
先看现象:如果 SHOW PROCESSLIST 里大量 INSERT 卡在 Writing to net 或 Updating 状态,但 CPU 和内存不紧张,iostat -x 1 显示 %util 接近 100%、await 超过 20ms,基本能确定是磁盘 IO 瓶颈。尤其当业务日志表(比如 operation_log)每秒写入几百行以上,且用的是普通 SATA 盘或和主库共用同一块 NVMe,问题会立刻暴露。
注意:不是所有“写得慢”都该换磁盘——先确认是否真由 IO 引起。常见误判点:
• 没关 innodb_flush_log_at_trx_commit=1,导致每次事务都刷盘
• 日志表没建好索引,INSERT ... SELECT 或触发器引发隐式锁等待
• 表引擎是 MyISAM,写操作全局锁表
把日志表迁到独立高性能磁盘,具体怎么操作?
核心不是“挂一块新盘”就完事,而是让 MySQL 真正把数据文件落到那块盘上。关键路径只有两个:表空间路径(InnoDB)或数据目录(MyISAM)。现代部署几乎全是前者。
- 确认目标磁盘已挂载且有写权限,比如挂载点是
/data/logdisk - 新建专用表空间:
CREATE TABLESPACE log_ts ADD DATAFILE '/data/logdisk/log_ts.ibd' ENGINE=InnoDB; - 迁移表(以
app_log为例):ALTER TABLE app_log TABLESPACE log_ts; - 验证位置:
SELECT FILE_NAME FROM INFORMATION_SCHEMA.FILES WHERE TABLE_NAME='app_log';应返回/data/logdisk/log_ts.ibd
⚠️ 容易踩的坑:
• ALTER TABLE ... TABLESPACE 要求 MySQL 5.7.6+,且表不能有全文索引或虚拟列
• 迁移过程会锁表(online DDL 可缓解,但需加 ALGORITHM=INPLACE)
• 新表空间路径必须由 MySQL 用户(如 mysql)可读写,否则启动报错 Operating system error number 13
innodb_log_group_home_dir 和日志表物理分离有关系吗?
没有。这个配置只控制 InnoDB 的重做日志(ib_logfile0/1)存放位置,影响的是崩溃恢复和事务持久性,和你的业务日志表(比如 user_action_log)的物理存储完全无关。把它挪到高速盘对写入性能提升微乎其微,除非你同时在扛极高 TPS 且重做日志频繁切换。
真正该关注的是:
• innodb_log_file_size:太小会导致频繁 checkpoint,间接加重 IO;建议设为 innodb_buffer_pool_size 的 25% 左右
• sync_binlog 和 innodb_flush_log_at_trx_commit:若日志表不要求强一致性(如仅用于审计),可临时调成 0 或 2,IO 压力立降 50%+
• 避免把 binlog 也写到同一块日志盘——它和表数据 IO 模式不同(顺序写 vs 随机写),混跑反而互相干扰
为什么单独挂 SSD 还是卡?可能漏了这些点
硬件升级后没变快,大概率是软件层没对齐。最常被忽略的三个点:
- 文件系统挂载参数不对:
/data/logdisk必须用noatime,nodiratime,barrier=0(ext4)或noatime(xfs),否则每次写都触发元数据更新 - MySQL 没用 O_DIRECT:
innodb_flush_method=O_DIRECT必须开启,否则 Linux page cache 和 InnoDB buffer pool 双重缓存,浪费内存还增加拷贝开销 - 日志表结构本身拖后腿:比如
TEXT字段存大 JSON、没设ROW_FORMAT=COMPRESSED、或者用AUTO_INCREMENT主键但在高并发下争抢热点页
真实场景中,见过把 NVMe 挂上去却因 mount -o defaults 导致 await 从 0.3ms 回升到 8ms 的案例。IO 瓶颈从来不是单点问题,磁盘只是最后一环。



















