mdl锁视图-j9九游会登录
mdl锁视图简介
社区版mysql如果不打开performance_schema开关,则无法获取表元数据锁(mdl)的详细信息,但通常情况下performance_schema默认关闭,当用户遇到类似“waiting for metadata lock”的问题而阻塞dml或ddl后,由于无法确定各个会话之间的关联关系,只能重启实例,增加了解决问题的成本,对业务产生了较大影响。
在业务场景较复杂的情况下,一旦涉及对数据库元数据的互斥操作(如ddl、lock table等),会频繁发生操作的会话被其他会话阻塞的问题,给用户带来很大的困扰。
针对以上问题,华为云rds for mysql推出了mdl锁视图特性,可以查看数据库各会话持有和等待的元数据锁信息,用户可以有效进行系统诊断,优化自身业务,有效降低对业务影响。
mdl锁视图详解
mdl锁视图以系统表的形式呈现,该表位于“information_schema”下,表名称是“metadata_lock_info”。表结构如下所示。
desc information_schema.metadata_lock_info; --------------- ----------------------- --------- ------ ---------- --------| | field | type | null |key |default | extra | --------------- ----------------------- --------- ------ ---------- --------| | thread_id | bigint(20) unsigned | no | | 0 | | | lock_status | varchar(24) | no | | | | | lock_mode | varchar(24) | yes | | null | | | lock_type | varchar(30) | yes | | null | | | lock_duration | varchar(30) | yes | | null | | | table_schema | varchar(64) | yes | | null | | | table_name | varchar(64) | yes | | null | | --------------- ----------------------- --------- ------ ---------- --------|
|
序号 |
字段名 |
字段定义 |
字段说明 |
|---|---|---|---|
|
0 |
thread_id |
bigint(20) unsigned |
会话id。 |
|
1 |
lock_status |
varchar(24) |
mdl锁的两种状态。
|
|
2 |
lock_mode |
varchar(24) |
加锁的模式,如mdl_shared 、mdl_exclusive 、mdl_shared_read、mdl_shared_write等。 |
|
3 |
lock_type |
varchar(30) |
mdl锁的类型,如table metadata lock、schema metadata lock、global read lock、tablespace lock等。 |
|
4 |
lock_duration |
varchar(30) |
mdl锁范围,取值如下:
|
|
5 |
table_schema |
varchar(64) |
数据库名,对于部分global级别的mdl锁,该值为空。 |
|
6 |
table_name |
varchar(64) |
表名,对于部分global级别的mdl锁,该值为空。 |
mdl锁视图使用示例
使用场景:长时间未提交事务,阻塞ddl,继而阻塞所有同表的操作。
|
表名 |
会话 |
|||
|
session2 |
session3 |
session4 |
session5 |
|
|
t1 |
begin; select * from t1; |
- |
- |
- |
|
t2 |
- |
begin; select * from t2; |
- |
- |
|
t3 |
- |
- |
truncate table t2; (blocked) |
- |
|
t4 |
- |
- |
- |
begin; select * from t2; (blocked) |
mdl锁视图案例分析
问题描述
用户发现对表t2执行truncate操作一直被阻塞后,业务流程中对表t2执行查询操作也全部被阻塞。
排查分析
- 无mdl锁视图
当发现ddl语句被阻塞后,执行show processlist查看线程信息,结果如下所示。
show processlist; ------ -------- -------------- -------- ----------- ---------- -----------------------------------|-------------------------| | id | user | host | db | command | time | state |info | --------------- ----------------------- ----------- ---------- ----------------------------------- -------------------------| | 2 | root | localhost | test | sleep | 73 | | null | | 3 | root | localhost | test | sleep | 63 | | null | | 4 | root | localhost | null | query | 35 | waiting for table metadata lock | truncate table test.t2 | | 5 | root | localhost | test | query | 17 | waiting for table metadata lock | select * from test.t2 | | 6 | root | localhost | test | query | 0 | starting | show processlist | ------ -------- -------------- -------- ----------- ---------- -----------------------------------|-------------------------|
上述线程列表信息显示:
- id=4的会话执行truncate操作时被其他会话持有的table metadata lock阻塞。
- id=5的会话执行查询操作时同样被阻塞。
- 无法确定哪个会话阻塞了id=4的会话和id=5的会话。
此时,如果随机kill其他会话会给线上业务带来很大风险,因此只能等待其他会话释放该mdl锁。
- 使用mdl锁视图
执行select * from information_schema.metadata_lock_info查看元数据锁信息,结果如下所示。
select * from information_schema.metadata_lock_info; ------------- ------------- -------------------------- ---------------------- ------------------- ---------------- ---------------- | thread_id | lock_status | lock_mode | lock_type | lock_duration | table_schema | table_name | ------------- ------------- -------------------------- ---------------------- ------------------- ---------------- ---------------- | 2 | granted | mdl_shared_read | table metadata lock | mdl_transaction | test | t1 | | 3 | granted | mdl_shared_read | table metadata lock | mdl_transaction | test | t2 | | 4 | granted | mdl_intention_exclusive | global read lock | mdl_statement | | | | 4 | granted | mdl_intention_exclusive | schema metadata lock | mdl_transaction | test | | | 4 | pending | mdl_exclusive | table metadata lock | | test | t2 | | 5 | pending | mdl_shared_read | table metadata lock | | test | t2 | ------------- ------------- -------------------------- ---------------------- ------------------- ---------------- ----------------
结合show processlist的结果,从元数据锁视图中可以明显看出:
上述线程信息和元数据锁视图信息显示:
- thread_id=4的会话正在等待表t2的metadata lock。
- thread_id=3的会话持有表t2的metadata lock,该mdl锁为事务级别,因此只要thread_id=3的会话的事务不提交,thread_id=4的会话将会一直阻塞。
因此,用户只需在thread_id=3的会话中执行命令commit或终止thread_id=3的会话,便可以让业务继续运行。
相关文档
意见反馈
文档内容是否对您有帮助?
如您有其它疑问,您也可以通过华为云社区问答频道来与我们联系探讨