连载中 15/22

定位工具箱:performance_schema 与 sys schema 实战

2026-05-09 · 2651 阅读 · 0 评论 · 0 赞

凌晨三点的 CPU

慢日志只记录「超过阈值的已完成查询」,但老王遇到的是另一类问题:凌晨三点 CPU 突然 90%,可慢日志里什么都没有——查询可能没到阈值,也可能问题根本不是慢 SQL,而是锁等待、长事务在拖累全场。这时候需要的是 MySQL 自带的体检仪:performance_schema(性能数据采集)+ sys schema(人话视图)。8.0 默认全开,开箱即用。

第一问:谁在消耗我的时间

performance_schema 把每条 SQL 按指纹(digest)聚合——同构的查询(只差字面值)归并统计,从此 TOP SQL 不再靠猜:

SELECT DIGEST_TEXT,
       COUNT_STAR                                  AS exec_cnt,
       ROUND(SUM_TIMER_WAIT / 1e12, 1)             AS total_sec,
       ROUND(AVG_TIMER_WAIT / 1e9, 1)              AS avg_ms,
       SUM_ROWS_EXAMINED                           AS examined
FROM performance_schema.events_statements_summary_by_digest
WHERE SCHEMA_NAME = "orders_db"
ORDER BY SUM_TIMER_WAIT DESC
LIMIT 10;

计时单位是皮秒,除以 1e12 换秒、1e9 换毫秒。解读两个信号:avg_ms 高的见一个修一个(EXPLAIN 走起);examined 巨大而返回极少的,是索引问题的惯犯——这和慢日志的 Rows_examined 是同一个思想,只是聚合视角。

第二问:此刻谁连着我

SELECT thd_id, conn_id, user, db, command,
       statement_latency, current_statement
FROM sys.session
WHERE command != "Sleep"
ORDER BY statement_latency DESC;

sys.session 是 processlist 的增强版:多出每连接当前正在执行的语句和耗时。排查「CPU 飙高」先看这里,抓到现行连接再决定 KILL。再配合第一问的 digest,能分辨「某条 SQL 偶发慢」还是「某条 SQL 被疯狂执行」。

第三问:长事务与锁等待

# 长事务:跑了多久、锁了多少行、改了多少行
SELECT trx_id, trx_started,
       TIMESTAMPDIFF(SECOND, trx_started, NOW()) AS run_sec,
       trx_rows_locked, trx_rows_modified
FROM information_schema.innodb_trx
ORDER BY trx_started
LIMIT 10;

# 锁等待现场:谁堵谁、各持什么锁、SQL 原文
SELECT * FROM sys.innodb_lock_waits;

长事务是第 7 篇警告过的 undo 连坐源头,run_sec 超过分钟级的都要盘问。sys.innodb_lock_waits 则把「阻塞者线程、被阻塞者线程、等待的锁、双方的 SQL」一张表摆齐,死锁隐患(第 9 篇)现场勘查神器。

彩蛋:MDL 元数据锁排查

还有一种玄学:ALTER 卡住,全表读写跟着卡死——元数据锁(MDL)。默认没开采集,先开启再看:

UPDATE performance_schema.setup_instruments SET ENABLED = "YES"
WHERE NAME = "wait/lock/metadata/sql/mdl";
SELECT * FROM performance_schema.metadata_locks
WHERE LOCK_STATUS = "PENDING";

PENDING 的就是排队申请者,顺着就能找到压着表不放的长事务——大表 DDL 的完整作战在第 19 篇。

速查表

症状第一落点
CPU 高 / 整体变慢sys.session 抓现行 + digest 找 TOP SQL
查询偶发变慢sys.innodb_lock_waits 看是否在排队
磁盘空间异常膨胀innodb_trx 长事务 + undo 堆积
DDL 卡死连锁堵metadata_locks 找 PENDING 与持有者
哪些表读写最重sys.schema_table_statistics

仪表盘配齐,内因看清楚了,下一篇看外因:应用的连接池怎么配,为什么 1000 个连接反而拖垮 8 核机器。

咖啡凉了,记得趁热喝。

☕
503

10 年全栈工程师 · 503咖啡馆主理人

#MySQL#performance_schema#sys schema#锁等待#长事务

评论 (0)

热门推荐

连载中 11/22

主从搭建实操:从零配出一主两从

光讲原理不过瘾?手把手搭一主两从:my.cnf 六个参数、复制账号、GTID、CHANGE REPLICATION SOURCE TO、SHOW REPLICA STATUS 验收,附翻车排查清单。

#MySQL#主从复制#GTID#主从搭建#高可用
2026-05-07 · 10101 阅读 · 0 评论 · 0 赞
连载中 16/22

连接池:HikariCP 参数与连接风暴

连接池不是越大越好:8 核机器配 1000 连接反而更慢的数学原理,HikariCP 四个必调参数,maxLifetime 与 wait_timeout 的隐形陷阱。

#MySQL#连接池#HikariCP#maxLifetime#连接风暴
2026-05-10 · 9873 阅读 · 0 评论 · 0 赞
连载中 4/16

缓存穿透:恶意 ID 打穿 MySQL 的四道防线

请求的数据在缓存和数据库里都不存在时,缓存形同虚设。聊聊参数校验、空值缓存、布隆过滤器、限流熔断四道防线的原理与组合打法。

#Redis#缓存穿透#布隆过滤器#高可用
2026-05-16 · 9294 阅读 · 21 评论 · 287 赞