深色模式
典型故障案例
摘要:数据库故障大多集中在锁、复制、连接、磁盘四类。本文按「现象 → 定位命令 → 处置 → 事后改进」的套路给出四个高频案例,可直接照搬排查路径。
适用环境
bash
# 故障定位三件套:先看存活、再看当前会话、再看错误日志
mysqladmin -uroot -p ping
mysql -uroot -p -e "SELECT * FROM information_schema.processlist WHERE time > 10 ORDER BY time DESC LIMIT 20\G"
tail -n 100 /data/mysql/log/mysqld.err1
2
3
4
2
3
4
案例一:锁等待,接口大面积超时
现象:应用报 Lock wait timeout exceeded,写入卡住。
sql
-- 1. 找出运行时间最长的事务
SELECT trx_id, trx_started, trx_rows_modified, trx_query
FROM information_schema.innodb_trx ORDER BY trx_started LIMIT 10;
-- 2. 查看锁等待关系
SELECT waiting_pid, waiting_query, blocking_pid, blocking_query
FROM sys.innodb_lock_waits; -- MySQL 5.7+ 的 sys 库
-- 3. 定位到 PID 后终止(需业务确认)
KILL 12345;1
2
3
4
5
6
7
8
9
10
2
3
4
5
6
7
8
9
10
改进:事务尽量短小、避免事务内调用外部接口;为更新条件建索引;设置 innodb_lock_wait_timeout 与语句超时。
案例二:主从不一致
现象:SHOW REPLICA STATUS 报 1032(找不到行)或 1062(主键冲突),复制中断。
sql
SHOW REPLICA STATUS\G -- 看 Last_SQL_Error / Last_SQL_Errno1
bash
# 查看具体出错的 binlog 事件
mysqlbinlog --start-position=<Exec_Master_Log_Pos> /data/mysql/data/binlog.0000NN | head -n 601
2
2
处置原则:
- 先确认从库数据是否可丢弃 → 重新做一次全量同步最干净。
- 不能重建时,用
pt-table-sync对比并修复差异(先在测试环境验证)。
bash
pt-table-sync --print --sync-to-master h=10.0.1.11,u=root,p=密码,D=shopdb,t=orders
# 确认无误后把 --print 换成 --execute1
2
2
危险
不要用 SET GLOBAL sql_slave_skip_counter=1 反复跳过错误来「恢复」复制,这会让主从数据差异持续扩大,最终无法修复。
案例三:连接数打满
现象:应用报 Too many connections,运维也登不进去。
sql
-- 管理员保留连接(MySQL 8.0 默认给 root 额外 1 个连接)
SELECT user, host, count(*) FROM information_schema.processlist GROUP BY user ORDER BY 3 DESC;
SELECT id, time, state, LEFT(info, 60) FROM information_schema.processlist
WHERE command='Sleep' AND time > 300;1
2
3
4
2
3
4
处置:
- 临时调大
max_connections只是缓解,必须找出源头。 - 常见原因:应用连接池配置过大、慢查询堆积、连接未释放(事务未提交)。
- 批量清理长时间 Sleep 连接需谨慎,建议由应用侧重启实例释放。
案例四:磁盘写满
现象:实例只读或崩溃,日志出现 No space left on device。
bash
df -h /data
du -sh /data/mysql/data/* | sort -rh | head -n 10
ls -lhS /data/mysql/data/binlog.* | head -n 51
2
3
2
3
处置:
sql
-- 清理过期 binlog(确认从库已消费)
PURGE BINARY LOGS BEFORE '2026-10-01 00:00:00';1
2
2
bash
# 清理旧的备份与临时文件(确认不需要后再删)
find /data/backup -name '*.sql.gz' -mtime +7 -delete1
2
2
危险
磁盘满时千万不要直接 rm binlog 文件,会让 MySQL 的 binlog 索引与实际文件不一致,导致复制与启动异常;必须用 PURGE BINARY LOGS 命令清理。
事后通用改进
- 补监控告警(锁等待、复制延迟、连接水位、磁盘水位)。
- 写复盘:时间线、根因、影响、改进项与责任人。
- 把处置命令沉淀成巡检脚本或应急预案。