当前位置:Gxlcms > 数据库问题 > 【12】MySQL:锁处理

【12】MySQL:锁处理

时间:2021-07-01 10:21:17 帮助过:4人阅读

=az WHERE id=10008;

在另外一个 session 中执行:

  1. <span style="color: #000000;">use testdb1;
  2. UPDATE t_100w SET k1</span>=<span style="color: #800000;">‘</span><span style="color: #800000;">qz</span><span style="color: #800000;">‘</span> WHERE id=10008;

在另外一个 session 此时我们查看:

  1. show status like <span style="color: #800000;">‘</span><span style="color: #800000;">innodb_row_lock%</span><span style="color: #800000;">‘</span>;

结果:

技术图片

可以看到有一个 row lock 等待。

 

2. 查看哪个事务在等待:

  1. select * <span style="color: #0000ff;">from</span> information_schema.INNODB_TRX where trx_state=<span style="color: #800000;">‘</span><span style="color: #800000;">LOCK WAIT</span><span style="color: #800000;">‘</span>\G

结果:

技术图片

其中主要的几个参数:

trx_id:事务 ID

trx_state:事务状态

trx_mysql_thread_id:连接线程的 ID,就是 show processlist 看到的 ID。

trx_query:当前被阻塞的 SQL

 

3. 查看谁锁的:

  1. select * <span style="color: #0000ff;">from</span> sys.innodb_lock_waits\G

结果:

技术图片

locked_table:哪张表被锁住。

waiting_trx_id:等待的事务 ID。

waiting_pid:等待的线程号。

blocking_trx_id:锁源的事务 ID。

blocking_pid:锁源的线程号。

 

4. 查看锁源:

  1. select * <span style="color: #0000ff;">from</span> performance_schema.threads where processlist_id=3\G

通过上一步获取到的锁源 PID 查询:

技术图片

 

5. 找到具体锁的 SQL 是哪一个。

  1. <span style="color: #008080;">--</span><span style="color: #008080;"> 当前在执行的语句</span>
  2. <span style="color: #0000ff;">SELECT</span> <span style="color: #808080;">*</span> <span style="color: #0000ff;">FROM</span> performance_schema.`events_statements_current` <span style="color: #0000ff;">WHERE</span> thread_id<span style="color: #808080;">=</span><span style="color: #800000; font-weight: bold;">41</span><span style="color: #000000;">;
  3. </span><span style="color: #008080;">--</span><span style="color: #008080;"> 执行语句的历史</span>
  4. <span style="color: #0000ff;">SELECT</span> <span style="color: #808080;">*</span> <span style="color: #0000ff;">FROM</span> performance_schema.`events_statements_history` <span style="color: #0000ff;">WHERE</span> thread_id<span style="color: #808080;">=</span><span style="color: #800000; font-weight: bold;">41</span>;

 

涉及到锁监控的一些命令:

  1. show status <span style="color: #808080;">like</span> <span style="color: #ff0000;">‘</span><span style="color: #ff0000;">innodb_rows_lock%</span><span style="color: #ff0000;">‘</span>
  2. <span style="color: #0000ff;">select</span> <span style="color: #808080;">*</span> <span style="color: #0000ff;">from</span><span style="color: #000000;"> information_schema.innodb_trx;
  3. </span><span style="color: #0000ff;">select</span> <span style="color: #808080;">*</span> <span style="color: #0000ff;">from</span><span style="color: #000000;"> sys.innodb_lock_waits;
  4. </span><span style="color: #0000ff;">select</span> <span style="color: #808080;">*</span> <span style="color: #0000ff;">from</span><span style="color: #000000;"> performance_schema.threads;
  5. </span><span style="color: #0000ff;">select</span> <span style="color: #808080;">*</span> <span style="color: #0000ff;">from</span><span style="color: #000000;"> performance_schema.events_statements_current;
  6. </span><span style="color: #0000ff;">select</span> <span style="color: #808080;">*</span> <span style="color: #0000ff;">from</span> performance_schema.events_statements_history;

 

 

处理锁的问题

 

当我们发现锁并且定位到具体的 SQL 以后,就需要对该问题进行处理:

1. 当 SQL 不是很重要,不是什么大事务或者重要的事务的时候,我们可以通过 kill 的方式杀掉 processlist 中的 PID。

2. 当然最终的决绝办法还是让开发修改业务处理逻辑。

 

对于死锁,我们可以将其记录到日志中,设置方法:

  1. innodb_print_all_deadlocks <span style="color: #808080;">=</span> <span style="color: #800000; font-weight: bold;">1</span>

 

 

小结

 

业务中很容易出现锁的情况,毕竟开发水平参差不齐,有些烂 SQL 没法避免。这就需要我们使用慢日志结合锁监控一起,定位问题,最终优化解决问题。

【12】MySQL:锁处理

标签:block   process   rman   一起   roc   sql   src   结果   方法   

人气教程排行