亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb

首頁 > 數據庫 > MySQL > 正文

MySQL表結構變更你不可不知的Metadata Lock詳解

2024-07-25 19:08:46
字體:
來源:轉載
供稿:網友

前言

想必玩過mysql的人對Waiting for table metadata lock肯定不會陌生,一般都是進行alter操作時被堵住了,導致了我們在show processlist 時,看到線程的狀態是在等metadata lock。本文會對MySQL表結構變更的Metadata Lock進行詳細的介紹。

在線上進行DDL操作時,相對于其可能帶來的系統負載,其實,我們最擔心的還是MDL其可能導致的阻塞問題。

一旦DDL操作因獲取不到MDL被阻塞,后續其它針對該表的其它操作都會被阻塞。典型如下,如阻塞稍久的話,我們會看到Threads_running飆升,CPU告警。

mysql> show processlist;+----+-----------------+-----------+-----------+---------+------+---------------------------------+------------------------------------+| Id | User | Host | db | Command | Time | State  | Info  |+----+-----------------+-----------+-----------+---------+------+---------------------------------+------------------------------------+| 4 | event_scheduler | localhost | NULL | Daemon | 122 | Waiting on empty queue | NULL  || 9 | root | localhost | NULL | Sleep | 57 |   | NULL  || 12 | root | localhost | employees | Query | 40 | Waiting for table metadata lock | alter table slowtech.t1 add c1 int || 13 | root | localhost | employees | Query | 35 | Waiting for table metadata lock | select * from slowtech.t1 || 14 | root | localhost | employees | Query | 30 | Waiting for table metadata lock | select * from slowtech.t1 || 15 | root | localhost | employees | Query | 19 | Waiting for table metadata lock | select * from slowtech.t1 || 16 | root | localhost | employees | Query | 10 | Waiting for table metadata lock | select * from slowtech.t1 || 17 | root | localhost | employees | Query | 0 | starting  | show processlist  |+----+-----------------+-----------+-----------+---------+------+---------------------------------+------------------------------------+rows in set (0.00 sec)

如果發生在線上,無疑會影響到業務。所以,一般建議將DDL操作放到業務低峰期做,其實有兩方面的考慮,1. 避免對系統負載產生較大影響。2. 減少DDL被阻塞的概率。 

MDL引入的背景

MDL是MySQL 5.5.3引入的,主要用于解決兩個問題,

RR事務隔離級別下不可重復讀的問題

如下所示,演示環境,MySQL 5.5.0。

session1> begin;Query OK, 0 rows affected (0.00 sec)session1> select * from t1;+------+------+| id | name |+------+------+| 1 | a || 2 | b |+------+------+rows in set (0.00 sec)session2> alter table t1 add c1 int;Query OK, 2 rows affected (0.02 sec)Records: 2 Duplicates: 0 Warnings: 0session1> select * from t1;Empty set (0.00 sec)session1> commit;Query OK, 0 rows affected (0.00 sec)session1> select * from t1;+------+------+------+| id | name | c1 |+------+------+------+| 1 | a | NULL || 2 | b | NULL |+------+------+------+rows in set (0.00 sec)

可以看到,雖然是RR隔離級別,但在開啟事務的情況下,第二次查詢卻沒有結果。

主從復制問題

包括主從數據不一致,主從復制中斷等。

如下面的主從數據不一致。

session1> create table t1(id int,name varchar(10)) engine=innodb;Query OK, 0 rows affected (0.00 sec)session1> begin;Query OK, 0 rows affected (0.00 sec)session1> insert into t1 values(1,'a');Query OK, 1 row affected (0.00 sec)session2> truncate table t1;Query OK, 0 rows affected (0.46 sec)session1> commit;Query OK, 0 rows affected (0.35 sec)session1> select * from t1;Empty set (0.00 sec)

再來看看從庫的結果

session1> select * from slowtech.t1;+------+------+------+| id | name | c1 |+------+------+------+| 1 | a | NULL |+------+------+------+row in set (0.00 sec)

看看binlog的內容,可以看到,truncate操作記錄在前,insert操作記錄在后。

# at 7140#180714 19:32:14 server id 1 end_log_pos 7261 Query thread_id=31 exec_time=0 error_code=0SET TIMESTAMP=1531567934/*!*/;create table t1(id int,name varchar(10)) engine=innodb/*!*/;# at 7261#180714 19:32:30 server id 1 end_log_pos 7333 Query thread_id=32 exec_time=0 error_code=0SET TIMESTAMP=1531567950/*!*/;BEGIN/*!*/;# at 7333#180714 19:32:30 server id 1 end_log_pos 7417 Query thread_id=32 exec_time=0 error_code=0SET TIMESTAMP=1531567950/*!*/;truncate table t1/*!*/;# at 7417#180714 19:32:30 server id 1 end_log_pos 7444 Xid = 422COMMIT/*!*/;# at 7444#180714 19:32:34 server id 1 end_log_pos 7516 Query thread_id=31 exec_time=0 error_code=0SET TIMESTAMP=1531567954/*!*/;BEGIN/*!*/;# at 7516#180714 19:32:24 server id 1 end_log_pos 7611 Query thread_id=31 exec_time=0 error_code=0SET TIMESTAMP=1531567944/*!*/;insert into t1 values(1,'a')/*!*/;# at 7611#180714 19:32:34 server id 1 end_log_pos 7638 Xid = 421COMMIT/*!*/;

如果會話2執行的是drop table操作,還會導致主從中斷。

有意思的是,如果會話2執行的是alter table操作,其依舊會被阻塞,阻塞時間受innodb_lock_wait_timeout參數限制。

mysql> show processlist;+----+------+-----------+----------+---------+------+-------------------+---------------------------+| Id | User | Host | db | Command | Time | State  | Info   |+----+------+-----------+----------+---------+------+-------------------+---------------------------+| 54 | root | localhost | NULL | Query | 0 | NULL  | show processlist  || 58 | root | localhost | slowtech | Sleep | 1062 |   | NULL   || 60 | root | localhost | slowtech | Query | 11 | copy to tmp table | alter table t1 add c1 int |+----+------+-----------+----------+---------+------+-------------------+---------------------------+rows in set (0.00 sec)

MDL的基本概念

首先,看看官方的說法,

To ensure transaction serializability, the server must not permit one session to perform a data definition language (DDL) statement on a table that is used in an uncompleted explicitly or implicitly started transaction in another session.

The server achieves this by acquiring metadata locks on tables used within a transaction and deferring release of those locks until the transaction ends.

A metadata lock on a table prevents changes to the table's structure.

This locking approach has the implication that a table that is being used by a transaction within one session cannot be used in DDL statements by other sessions until the transaction ends.

從上面的描述可以看到,

1. MDL出現的初衷就是為了保護一個處于事務中的表的結構不被修改。

2. 這里提到的事務包括兩類,顯式事務和AC-NL-RO(auto-commit non-locking read-only)事務。顯式事務包括兩類:1. 關閉AutoCommit下的操作,2. 以begin或start transaction開始的操作。AC-NL-RO可理解為AutoCommit開啟下的select操作。

3. MDL是事務級別的,只有在事務結束后才會釋放。在此之前,其實也有類似的保護機制,只不過是語句級別的。

需要注意的是,MDL不僅僅適用于表,同樣也適用于其它對象,如下表所示,其中,"等待狀態"對應的是"show processlist"中的State。

MySQL,表結構,Metadata,Lock

為了提高數據庫的并發度,MDL被細分為了11種類型。

  • MDL_INTENTION_EXCLUSIVE
  • MDL_SHARED
  • MDL_SHARED_HIGH_PRIO
  • MDL_SHARED_READ
  • MDL_SHARED_WRITE
  • MDL_SHARED_WRITE_LOW_PRIO
  • MDL_SHARED_UPGRADABLE
  • MDL_SHARED_READ_ONLY
  • MDL_SHARED_NO_WRITE
  • MDL_SHARED_NO_READ_WRITE
  • MDL_EXCLUSIVE

常用的有MDL_SHARED_READ,MDL_SHARE D_WRITE及MDL_EXCLUSIVE,其分別用于SELECT操作,DML操作及DDL操作。其它類型的對應操作可參考源碼sql/mdl.h。

對于MDL_EXCLUSIVE,官方的解釋是,

/*
An exclusive metadata lock.
A connection holding this lock can modify both table's metadata and data.
No other type of metadata lock can be granted while this lock is held.
To be used for CREATE/DROP/RENAME TABLE statements and for execution of
certain phases of other DDL statements.
*/

簡而言之,MDL_EXCLUSIVE是獨占鎖,在其持有期間是不允許其它類型的MDL被授予,自然也包括SELECT和DML操作。

這也就是為什么DDL操作被阻塞時,后續其它操作也會被阻塞。

關于MDL的補充

1. MDL的最大等待時間由lock_wait_timeout參數決定,其默認值為31536000(365天)。在使用工具進行DDL操作時,這個值就不太合理。事實上,pt-online-schema-change和gh-ost對其就進行了相應的調整,其中,前者60s,后者3s。

2. 如果一個SQL語法上有效,但執行時報錯,如,列名不存在,其同樣會獲取MDL鎖,直到事務結束才釋放。

總結

以上就是這篇文章的全部內容了,希望本文的內容對大家的學習或者工作具有一定的參考學習價值,如果有疑問大家可以留言交流,謝謝大家對VeVb武林網的支持。


注:相關教程知識閱讀請移步到MYSQL教程頻道。
發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb
日韩有码在线视频| 一个人看的www欧美| 中文字幕亚洲字幕| 日韩av电影在线播放| 狠狠做深爱婷婷久久综合一区| 欧美高清无遮挡| 国产精品久久久999| 日韩av在线免费播放| 精品日韩视频在线观看| 国产欧美日韩综合精品| 亚洲天堂成人在线视频| 欧美午夜激情视频| 成人综合国产精品| 亚洲欧美自拍一区| 国产成人精品av在线| 久久青草精品视频免费观看| 91久久久久久久一区二区| 国产精品视频播放| 国产在线观看不卡| 久久久这里只有精品视频| 亚洲欧美国内爽妇网| 国产精品丝袜视频| 成人中心免费视频| 国产精品美女久久久免费| 中文字幕亚洲无线码在线一区| 欧美精品免费在线观看| 亚洲国产一区二区三区在线观看| 91高清在线免费观看| 欧美国产在线电影| 欧美日韩亚洲一区二区三区| 日韩影视在线观看| 精品国产美女在线| 国产在线视频2019最新视频| 亚洲视频在线观看网站| 在线视频欧美性高潮| 亚洲人成网7777777国产| 一区二区三区 在线观看视| 亚洲国产精品网站| 亚洲一区二区在线播放| 精品久久久久久久久久久久| 欧美成人激情图片网| 欧美激情极品视频| 中文字幕精品在线视频| 国产亚洲欧洲高清| 美日韩精品免费视频| 综合欧美国产视频二区| 亚洲色图美腿丝袜| 国产成人精品日本亚洲专区61| 国产精品永久在线| 久久视频国产精品免费视频在线| 日韩中文视频免费在线观看| 一区二区亚洲欧洲国产日韩| 黑人巨大精品欧美一区二区一视频| 欧美在线亚洲在线| 欧美精品成人91久久久久久久| 国产精品美女在线观看| 97人人爽人人喊人人模波多| 亚洲性av在线| 一区二区三区视频免费在线观看| 91精品久久久久久久久青青| 国产精品手机播放| 国产福利成人在线| 18性欧美xxxⅹ性满足| 中文字幕视频一区二区在线有码| 日韩av第一页| 欧美高清电影在线看| 欧美性猛交xxxx偷拍洗澡| 久久男人av资源网站| www.精品av.com| 欧美激情在线观看| 色哟哟入口国产精品| 国产精品狼人色视频一区| 久操成人在线视频| 亚洲国产欧美一区二区三区久久| 九九精品在线观看| 欧美日韩性生活视频| 亚洲国产成人在线视频| 欧美黄色小视频| 欧美成人全部免费| 中文字幕日韩免费视频| 欧美大学生性色视频| 成人午夜一级二级三级| 成人福利网站在线观看11| 日韩电影大全免费观看2023年上| 亚洲精品资源美女情侣酒店| 日韩中文字幕免费视频| 久热精品视频在线| 91精品国产色综合久久不卡98| 成人午夜黄色影院| 5278欧美一区二区三区| 久久精品久久精品亚洲人| 亚洲第一区在线| 日韩成人在线视频| 欧美一区在线直播| 欧美激情啊啊啊| 欧美午夜视频一区二区| 亚洲人成五月天| 国产欧美婷婷中文| 欧美极品欧美精品欧美视频| 国产精品99久久久久久人| 色狠狠av一区二区三区香蕉蜜桃| 成人免费网站在线| 久久综合88中文色鬼| 欧美成人免费va影院高清| 亚洲天堂av女优| 45www国产精品网站| 国产精品成人观看视频国产奇米| 国产欧美在线看| 成人网在线免费观看| 久久久精品视频成人| 久久久999精品免费| 国产亚洲人成a一在线v站| 亚洲欧美日本伦理| 亚洲视频一区二区三区| 91精品国产91| 久久国产精品影视| 亚洲第一中文字幕在线观看| 亚洲一区二区三区毛片| 亚洲欧美日韩久久久久久| 亚洲国产精品久久91精品| 欧美在线观看网站| 亚洲一区二区三区成人在线视频精品| 欧美又大又硬又粗bbbbb| 亚洲第一区第一页| 欧美亚洲视频在线看网址| 日韩精品亚洲精品| www.xxxx精品| 日本一欧美一欧美一亚洲视频| 国产视频精品免费播放| 亚洲free性xxxx护士hd| 欧美最顶级丰满的aⅴ艳星| 欧美xxxx14xxxxx性爽| 亚洲女人被黑人巨大进入al| 国产精品综合不卡av| 亲爱的老师9免费观看全集电视剧| 色婷婷**av毛片一区| 国产精品va在线播放我和闺蜜| 亚洲欧美日韩第一区| 色综合91久久精品中文字幕| 国产一区玩具在线观看| 日韩欧美国产网站| 成人欧美一区二区三区在线湿哒哒| 91禁国产网站| 色婷婷综合成人| 国产亚洲精品久久久久久| 欧美贵妇videos办公室| 91高清免费视频| 久久精品国产2020观看福利| 欧美高清视频在线| 久久精品成人动漫| 日韩视频免费大全中文字幕| 欧美专区在线视频| 国产一区二区三区三区在线观看| 国产精品久久久久福利| 精品久久久久久亚洲国产300| 日韩精品在线视频观看| 狠狠色香婷婷久久亚洲精品| 久久91亚洲精品中文字幕奶水| 日韩精品高清在线观看| 久久精品亚洲国产| 久久久久久国产精品久久| 日韩网站在线观看| 亚洲激情视频在线| 97香蕉超级碰碰久久免费的优势|