为什么用这个视图
并发写同一批行时会出现锁等待:sys.innodb_lock_waits 把等待方与阻塞方的连接、语句、锁对象和等待时长放在一个视图里,一眼就能看出谁在挡谁。MySQL 5.7 起提供 sys 库,8.0 上底层数据来自 performance_schema 的锁表,不再需要手工拼接复杂的查询。
基本信息
| 适用平台 | MySQL 5.7+(sys schema);8.0 底层为 performance_schema |
|---|---|
| 核心视图 | sys.innodb_lock_waits:等待方、阻塞方、锁对象、等待时长 |
| 配套视图 | information_schema.innodb_trx:事务起点与当前语句 |
| 关键列 | wait_age 已等待时长,持续增长说明阻塞方没有释放 |
| 处置顺序 | 先确认业务归属再决定处理,不要盲目终止连接 |
典型使用场景
- 应用报锁等待超时,定位到底是谁持有锁
- DDL 被卡住时检查是否有长事务在跑
- 批量更新撞上在线业务,找出冲突的表与索引区间
- 监控里等待时长持续增长时第一时间介入
- 复盘锁竞争频率,指导事务拆分与批次调小
排查语句
排查语句
-- 一条语句看清谁在等谁
SELECT wait_started, wait_age, locked_table, locked_index,
waiting_pid, waiting_query,
blocking_pid, blocking_query
FROM sys.innodb_lock_waits;
-- 关联事务信息:阻塞事务开了多久、当前在跑什么
SELECT trx_id, trx_state, trx_started, trx_mysql_thread_id, trx_query
FROM information_schema.innodb_trx;
-- DDL 被阻塞时还要看元数据锁
SELECT * FROM sys.schema_table_lock_waits;关键列读法
| 列 | 含义 | 怎么判断 |
|---|---|---|
| wait_age | 本次等待已持续多久 | 持续增长说明阻塞方没有释放 |
| waiting_query | 等待方的 SQL | 定位被卡住的业务 |
| blocking_pid | 阻塞事务的连接号 | 对应到业务后再处置 |
| locked_table / locked_index | 冲突的表与索引 | 判断热点行还是索引区间 |
| trx_started | 阻塞事务的开始时间 | 越久越可疑,常见于忘了提交 |
终止阻塞连接是最后手段:它可能是核心业务事务,回滚本身还要时间,可能放大影响。先看 blocking_query 与业务归属,能等就等,能联系到业务方就先联系。
链式阻塞时视图里会同时出现多组等待关系,串起来看才能找到最上游的源头事务,只盯着第一个等待方很容易误判。