排查linux CentOS7.6的mysql磁盘 I/O 延迟过高问题
一,问题影响
磁盘 I/O 延迟过高会直接导致:
- 系统整体卡顿:所有依赖磁盘读写的操作(如日志写入、数据库读写、文件存储)都会变慢
- 业务响应超时:数据库查询、接口调用、服务启动等耗时大幅增加,甚至引发超时
- 服务稳定性下降:严重时会导致进程夯住、服务宕机,影响业务连续性
二,排查步骤(按优先级)
快速定位高 I/O 进程
登录目标主机 ,执行以下命令:# 实时查看I/O占用最高的进程(按%iowait排序)iostat-x15# 或更直观的进程级I/O监控iotop-oP
- 重点关注 %util(磁盘利用率,接近 100% 说明磁盘饱和)、r_wait/w_wait(读写等待时间)
- 找到占用 I/O 最高的进程 PID,进一步排查对应服务(如 MySQL、日志服务、备份任务等)
分析磁盘分区与挂载
# 查看sda分区与挂载情况df-h/dev/sda* lsblk# 检查是否存在分区满、inode耗尽df-i
- 若分区使用率 > 90%,会直接导致 I/O 飙升,需清理冗余数据
- 检查挂载参数是否异常(如错误使用同步挂载、noatime 未配置等)
- 针对性排查常见场景
| 常见场景 | 排查命令 | 处理建议 |
|---|---|---|
| 数据库 I/O 过高 | mysqladmin processlist / show processlist; | 优化慢查询、调整 InnoDB 缓冲池、分库分表 |
| 日志 / 备份任务 | du -sh /var/log/* /ps aux grep backup | 清理过期日志、调整备份时间至业务低峰 |
| 磁盘硬件故障 | smartctl -a /dev/sda | 检查磁盘健康状态,若有坏道需更换磁盘 |
| 系统 IO 调度器问题 | cat /sys/block/sda/queue/scheduler | 机械盘用 mq-deadline/noop,SSD 用 none |
三,分析iostat -x 1 5结果,查看I/O占用
[root@db ~]# iostat -x 1 5Linux3.10.0-957.el7.x86_64(26)2026年04月13日 _x86_64_(52CPU)avg-cpu: %user %nice %system %iowait %steal %idle0.900.000.170.860.0098.07Device: rrqm/s wrqm/s r/s w/s rkB/s wkB/s avgrq-sz avgqu-sz await r_await w_await svctm %util sda0.020.760.2355.5112.833256.20117.290.040.7711.150.730.372.07dm-00.000.000.020.101.290.9539.420.0029.636.7333.729.910.11dm-10.000.000.030.030.100.118.000.0043.8414.4770.655.400.03dm-20.000.000.2156.1411.433255.13115.940.040.7111.440.670.352.00avg-cpu: %user %nice %system %iowait %steal %idle2.350.000.331.750.0095.57Device: rrqm/s wrqm/s r/s w/s rkB/s wkB/s avgrq-sz avgqu-sz await r_await w_await svctm %util sda0.000.000.0085.000.004072.0095.811.5318.090.0018.099.2478.50dm-00.000.000.000.000.000.000.000.000.000.000.000.000.00dm-10.000.000.000.000.000.000.000.000.000.000.000.000.00dm-20.000.000.0082.000.004144.00101.071.5318.730.0018.739.5678.40avg-cpu: %user %nice %system %iowait %steal %idle1.890.000.270.870.0096.98Device: rrqm/s wrqm/s r/s w/s rkB/s wkB/s avgrq-sz avgqu-sz await r_await w_await svctm %util sda0.000.000.0054.000.003160.00117.040.9317.350.0017.357.8342.30dm-00.000.000.000.000.000.000.000.000.000.000.000.000.00dm-10.000.000.000.000.000.000.000.000.000.000.000.000.00dm-20.000.000.0053.000.002960.00111.700.9317.660.0017.667.9642.20avg-cpu: %user %nice %system %iowait %steal %idle0.980.000.271.600.0097.15Device: rrqm/s wrqm/s r/s w/s rkB/s wkB/s avgrq-sz avgqu-sz await r_await w_await svctm %util sda0.000.000.0092.000.009036.00196.432.3224.620.0024.627.0164.50dm-00.000.000.000.000.000.000.000.000.000.000.000.000.00dm-10.000.000.000.000.000.000.000.000.000.000.000.000.00dm-20.000.000.0095.000.009084.00191.242.3223.820.0023.826.8064.60avg-cpu: %user %nice %system %iowait %steal %idle2.330.000.401.750.0095.51Device: rrqm/s wrqm/s r/s w/s rkB/s wkB/s avgrq-sz avgqu-sz await r_await w_await svctm %util sda0.000.000.0089.000.003916.0088.001.5518.020.0018.027.3965.80dm-00.000.000.000.000.000.000.000.000.000.000.000.000.00dm-10.000.000.000.000.000.000.000.000.000.000.000.000.00dm-20.000.000.0086.000.003868.0089.951.5418.600.0018.607.6465.70[root@db ~]#- 磁盘确实在持续高写压力
- sda 利用率 %util 瞬间冲到 44% → 66% → 71%
- 几乎全是写:r/s≈0,w/s 46~92,wkB/s 3000~5000
- await 13~20ms
已排查系统盘空间、inode 都完全正常。mysql的库都在/home里
服务器是离线环境,没有安装iotop工具,若有网,可按照iotop排查
先装 iotop:
yuminstall-yiotop然后执行:
iotop-oP- 更通用的工具排查
# 按IO排序看进程psaux--sort=-pcpu,-rss# 看哪个目录在疯狂写du-sh--exclude=/proc /home/*|sort-rh或者
# 实时看文件写入lsof|grep-E'REG|DIR'|grep-E'/home'|head-20- 排查出可疑进程后
- 若存在非mysql的进程,比如python,可以看看这个 Python 脚本在干嘛,比如pid为455850
pstree-p455850ll /proc/455850/cwdls-l/proc/455850/fd|grepmysql- 看 MySQL 当前在跑什么 SQL
show processlist;或者
SELECT * FROM information_schema.processlist WHERE Command!='Sleep'ORDER BY Time DESC;