MySQL出现Lock wait timeout exceeded报错时如何找出持有锁的源头事务

浅强大大_8933

浅强大大_8933

2026-11-08

961人浏览

原创

真正要查的是“开了很久却没提交”的空挂事务,需筛选INNODB_TRX中trx_state='RUNNING'、trx_query为空且trx_started早于当前60秒的记录,并关联PROCESSLIST确认Sleep状态下的幽灵连接及blocking_thread_id后KILL。

mysql出现lock wait timeout exceeded报错时如何找出持有锁的源头事务

查INNODB_TRX找长时间RUNNING且trx_query为空的事务

真正卡住别人的,往往不是正在跑SQL的线程,而是开了事务却什么都没执行、就挂着不动的“空挂事务”。这类事务在INNODB_TRX里表现为trx_state = 'RUNNING'、trx_query为NULL或空字符串,且trx_started时间远早于当前(比如超过60秒)。它们极大概率是应用异常中断、RPC超时未处理、或@Transactional方法里catch了异常却忘了rollback。

运行这条语句快速筛出可疑目标:

SELECT trx_id, trx_mysql_thread_id, trx_started, trx_state, trx_query, trx_isolation_level
FROM information_schema.INNODB_TRX
WHERE trx_state = 'RUNNING'
  AND trx_started <p>重点关注<code>trx_mysql_thread_id</code>字段值,它就是后续要关联确认和可能KILL的线程ID。</p><h3>用INNODB_LOCK_WAITS确认谁在堵谁</h3><p><code>INNODB_TRX</code>只告诉你“有长事务”,但不确定它是否真在阻塞别人。必须通过<code>INNODB_LOCK_WAITS</code>建立等待链路——它会明确告诉你哪个事务在等哪个事务。</p><p>执行以下查询:</p><pre class="brush:php;toolbar:false;">SELECT r.trx_id waiting_trx_id,
       r.trx_query waiting_query,
       b.trx_id blocking_trx_id,
       b.trx_query blocking_query,
       b.trx_mysql_thread_id blocking_thread_id
FROM INFORMATION_SCHEMA.INNODB_TRX r
INNER JOIN INFORMATION_SCHEMA.INNODB_LOCK_WAITS w ON r.trx_id = w.requesting_trx_id
INNER JOIN INFORMATION_SCHEMA.INNODB_TRX b ON b.trx_id = w.blocking_trx_id;

如果返回结果为空,不代表没锁:可能是锁刚释放、或已触发死锁自动回滚(此时SHOW ENGINE INNODB STATUS\G末尾会有LATEST DETECTED DEADLOCK段落);如果有结果,blocking_query为空或只是简单SELECT,基本可断定是事务没提交导致锁滞留。

联查PROCESSLIST确认Sleep状态下的幽灵连接

很多阻塞源在SHOW PROCESSLIST里看起来毫无威胁:COMMAND = 'Sleep'、STATE = ''、INFO为空、但TIME高达几百甚至上千秒。这种“幽灵连接”不占CPU、不打日志,却持续持有行锁或间隙锁。

MySQL8 CRM Schema Design Expert
MySQL8 CRM Schema Design Expert

面向 CRM 系统的 MySQL 8 数据库模式设计。当用户需要为客户关系管理(CRM)系统设计、评审、优化或生成数据库模式时,应使用此项技能。

下载

用这个语句直接定位:

SELECT p.ID, p.USER, p.HOST, p.DB, p.COMMAND, p.TIME, p.STATE, p.INFO,
       t.trx_id, t.trx_started, t.trx_state
FROM information_schema.PROCESSLIST p
JOIN information_schema.INNODB_TRX t ON p.ID = t.trx_mysql_thread_id
WHERE p.COMMAND = 'Sleep'
  AND t.trx_state = 'RUNNING'
  AND p.TIME > 300
ORDER BY t.trx_started;

关键判断点:

  • HOST和USER能帮你快速圈定是哪个应用实例或开发终端连上来的
  • 别碰USER = 'system user'的线程,那是主从同步线程,KILL会导致数据不一致
  • TIME > 300且INFO为空 → 大概率是连接池归还了连接但没清理事务上下文

KILL blocking_thread_id,不是报错线程ID

报错语句本身只是第一个等不及的受害者,KILL它只会让当前请求失败,阻塞源还在继续霸占锁。必须KILL的是blocking_thread_id(来自上一步INNODB_LOCK_WAITS或PROCESSLIST联查结果)。

执行:

KILL <blocking_thread_id>;</blocking_thread_id>

注意:

  • MySQL 5.7中KILL后事务会回滚,锁立即释放,但需确认该事务无副作用(比如它正处在资金扣减中途)
  • 若blocking_query是SLEEP(300)或调外部HTTP接口,说明是应用逻辑缺陷,不是临时应急能解决的
  • 线上环境建议先SELECT确认线程归属,再KILL;避免误杀定时任务或监控采集连接

最棘手的情况,是那个持锁事务既不执行SQL、也不报错、trx_query为空、PROCESSLIST里COMMAND = 'Sleep'、TIME持续增长——它安静得像不存在,却能让所有写请求排队超时。这种事务一旦漏掉,问题就会反复出现。

相关专题

更多
mysql修改数据表名
mysql修改数据表名

MySQL修改数据表:1、首先查看数据库中所有的表,代码为:‘SHOW TABLES;’;2、修改表名,代码为:‘ALTER TABLE 旧表名 RENAME [TO] 新表名;’。php中文网还提供MySQL的相关下载、相关课程等内容,供大家免费下载使用。

2023.06.20

2513

6

MySQL创建存储过程
MySQL创建存储过程

存储程序可以分为存储过程和函数,MySQL中创建存储过程和函数使用的语句分别为CREATE PROCEDURE和CREATE FUNCTION。使用CALL语句调用存储过程智能用输出变量返回值。函数可以从语句外调用(通过引用函数名),也能返回标量值。存储过程也可以调用其他存储过程。php中文网还提供MySQL创建存储过程的相关下载、相关课程等内容,供大家免费下载使用。

2023.06.21

1519

5

mongodb和mysql的区别
mongodb和mysql的区别

mongodb和mysql的区别:1、数据模型;2、查询语言;3、扩展性和性能;4、可靠性。本专题为大家提供mongodb和mysql的区别的相关的文章、下载、课程内容,供大家免费下载体验。

2023.07.18

895

5

mysql密码忘了怎么查看
mysql密码忘了怎么查看

MySQL是一个关系型数据库管理系统,由瑞典MySQL AB 公司开发,属于 Oracle 旗下产品。MySQL 是最流行的关系型数据库管理系统之一,在 WEB 应用方面,MySQL是最好的 RDBMS 应用软件之一。那么mysql密码忘了怎么办呢?php中文网给大家带来了相关的教程以及文章,欢迎大家前来阅读学习。

2023.07.19

3592

5

mysql创建数据库
mysql创建数据库

MySQL是一个关系型数据库管理系统,由瑞典MySQL AB 公司开发,属于 Oracle 旗下产品。MySQL 是最流行的关系型数据库管理系统之一,在 WEB 应用方面,MySQL是最好的 RDBMS 应用软件之一。那么mysql怎么创建数据库呢?php中文网给大家带来了相关的教程以及文章,欢迎大家前来阅读学习。

2023.07.25

6208

4

mysql默认事务隔离级别
mysql默认事务隔离级别

MySQL是一种广泛使用的关系型数据库管理系统,它支持事务处理。事务是一组数据库操作,它们作为一个逻辑单元被一起执行。为了保证事务的一致性和隔离性,MySQL提供了不同的事务隔离级别。php中文网给大家带来了相关的教程以及文章欢迎大家前来学习阅读。

2023.08.08

1319

3

sqlserver和mysql区别
sqlserver和mysql区别

SQL Server和MySQL是两种广泛使用的关系型数据库管理系统。它们具有相似的功能和用途,但在某些方面存在一些显著的区别。php中文网给大家带来了相关的教程以及文章,欢迎大家前来学习阅读。

2023.08.11

6471

4

mysql忘记密码
mysql忘记密码

MySQL是一种关系型数据库管理系统,关系数据库将数据保存在不同的表中,而不是将所有数据放在一个大仓库内,这样就增加了速度并提高了灵活性。那么忘记mysql密码我们该怎么解决呢?php中文网给大家带来了相关的教程以及其他关于mysql的文章,欢迎大家前来学习阅读。

2023.08.14

5562

7

mysql事务隔离级别
mysql事务隔离级别

mysql规范中定义了四种事务隔离级别,不同的隔离级别对事务的处理有所不同。本专题为大家提供mysql事务隔离级别相关的文章内容,大家可以免费体验。

2023.08.16

7534

11

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
PostgreSQL vs MySQL
PostgreSQL vs MySQL

共1课时 | 194人学习