快速定位MySQL锁等待问题

Posted 运维之美

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了快速定位MySQL锁等待问题相关的知识,希望对你有一定的参考价值。

演示MySQL版本为MySQL5.7.22

通过sys.innodb_lock_waits 视图 表查看Innodb 当前事务锁等待信息,默认是按照发生锁等待的开始时间升序排列的;wait_started字段即innodb_trx 表的trx_wait_started字段

sys.innodb_lock_waits视图数据来源:


information_schema.innodb_trx, information_schema.innodb_locks ,information_schema.innodb_lock_waits


提示:

mysql8.0之后的版本,sys.innodb_lock_waits 视图信息来源自information_schema.innodb_trx, performance_schema.data_locks, performance_schema.data_wait_lock


查看sys下的视图innodb_lock_waits:


\'tidb03\' root@localhost 16:46:03 test001>select TABLE_SCHEMA , TABLE_NAME from information_schema.TABLES where table_type=\'view\' and TABLE_SCHEMA =\'sys\' and TABLE_NAME=\'innodb_lock_waits\';  
+--------------+-------------------+

| TABLE_SCHEMA | TABLE_NAME |

+--------------+-------------------+

| sys | innodb_lock_waits |

+--------------+-------------------+

1 row in set (0.00 sec)


会话一:​ 发起一个未提交的update事务


\'tidb03\' root@localhost 16:03:25 test001>select * from test001;

+----+----------+----------+---------------------+

| id | username | password | create_time |

+----+----------+----------+---------------------+

| 1 | 小花 | abc123 | 2021-09-19 13:31:07 |

+----+----------+----------+---------------------+

1 row in set (0.00 sec)



\'tidb03\' root@localhost 16:04:21 test001>begin;

Query OK, 0 rows affected (0.00 sec)



\'tidb03\' root@localhost 16:03:34 test001>update test001 set username=\'小白\' where id=1;

Query OK, 1 row affected (0.00 sec)

Rows matched: 1 Changed: 1 Warnings: 0



会话二:update更新同一条记录


\'tidb03\' root@localhost 16:04:04 test001>update test001 set username=\'大米\' where id=1;

Query OK, 1 row affected (9 min 32.98 sec)

Rows matched: 1 Changed: 1 Warnings: 0



会话三: 查看sys.innodb_lock_waits视图获取锁等待信息


\'tidb03\' root@localhost 16:06:24 sys>select * from sys.innodb_lock_waits\\G

*************************** 1. row ***************************

wait_started: 2021-09-20 16:04:20 ##发生锁等待的开始时间

wait_age: 00:02:25 ##锁已经等待了多久了,是一个时间格式的值

wait_age_secs: 145 ##锁已经等待了145s,是一个整型的数值,此字段是mysql5.7.9版本中新增

locked_table: `test001`.`test001` ##锁等待的表名称

locked_index: PRIMARY ##锁等待的索引名称

locked_type: RECORD ##锁等待的类型

waiting_trx_id: 47819075 ## 锁等待的事务id

waiting_trx_started: 2021-09-20 16:04:20 ##锁等待的开始时间
waiting_trx_age: 00:02:25 ## 发生锁等待的事务的总的等待时间

waiting_trx_rows_locked: 1 ##发生锁等待事务已经锁定的行数(如果是复杂的事务会累计)

waiting_trx_rows_modified: 0 ##发生锁等待事务已经修改的行数(如果是复杂的事务会累计)

waiting_pid: 204862 ##发生锁等待事务的processlist id 号

waiting_query: update test001 set username=\'大米\' where id=1 ##发生锁等待事务的sql语句文本

waiting_lock_id: 47819075:693:3:2 ## 发生锁等待的锁id

waiting_lock_mode: X ##发生锁等待的锁模式

blocking_trx_id: 47819074 ##持有锁的事务id

blocking_pid: 204829 ##持有锁的事务的processlist id号
blocking_query: NULL ##持有锁的事务的sql文本

blocking_lock_id: 47819074:693:3:2 ##持有锁的锁id

blocking_lock_mode: X ##持有锁的锁模式

blocking_trx_started: 2021-09-20 16:03:34 ##持有锁的事务的开始时间

blocking_trx_age: 00:03:11 ##持有锁的事务已经执行了多长时间

blocking_trx_rows_locked: 1 ##持有锁的事务锁定的行数

blocking_trx_rows_modified: 1 ##持有锁的事务需要修海的行数

sql_kill_blocking_query: KILL QUERY 204829 ##执行KILL 语句来杀死持有锁的查询语句(而不是终止会话)此字段MySQL5.7.9新增

sql_kill_blocking_connection: KILL 204829 ##执行KILL 语句来来终止持有锁的语句的会话,,此字段MySQL5.7.9新增

1 row in set, 3 warnings (0.01 sec)



以上是关于快速定位MySQL锁等待问题的主要内容,如果未能解决你的问题,请参考以下文章

InnoDB快速定位行锁争用会话的过程和操作

JUC并发编程 共享模式之工具 JUC CountdownLatch(倒计时锁) -- CountdownLatch应用(等待多个线程准备完毕( 可以覆盖上次的打印内)等待多个远程调用结束)(代码片段

12MySQL:锁处理

mysql 啥时候开启行级锁

mysql行锁等待异常

MySQL锁等待与死锁问题分析