關於MySQL建表對DML的影響

2021-08-07 19:54:15 字數 1431 閱讀 4933

今天一位同學問到線上曾經碰到過連續建表,導致阻塞普通的insert、update等。不過也沒有保留現場。因此有疑問為什麼建表會影響dml?

分析

首先這個現象不是在所有場景都會碰到(否則mysql的使用者們早就跳起來了)。

一來建表這個操作本身很快,只涉及到寫表定義檔案和初始化表空間。中間涉及到redo和undo的操作也很少(這裡只討論innodb表)。因此除非碰到磁碟io響應不了,否則多數情況下建表操作很快結束,不會「穩定復現」

二來即使由於io原因,建表過程執行時間較長,建表操作也不會阻塞一些dml操作。

因此只能從**出發看衝突的case。

假設session 1正在執行乙個create table操作,且由於io原因阻塞在寫表空間檔案這個步驟上。討論session2作如下操作的場景。

無主鍵表insert

此時insert操作由於需要申請系統自增主鍵,需要對dict_sys->mutex加鎖。而這個鎖需要等session1建表操作完成後才釋放,因此出現等待。

有外來鍵表的操作

此時session2需要判斷外來鍵一致性,需要對dict_sys->mutex加鎖。

這裡包含幾個方面:外來鍵約束的child表插入資料時和parent表刪除資料時,已經這兩個表的關聯外來鍵字段被修改時,均會觸發等待。

有同學會說我們線上這兩種情況都禁止了,是不是就不會因為這個鎖的原因導致阻塞dml?

新開啟表時

若這個insert操作需要新開啟乙個表時,需要根據表名從字典中取出資訊,也會觸發等待。

即使原來已經開啟過的表,也會因為執行了flush table或者表空間淘汰而要求下次訪問需要重新開啟。

影響的其他操作

順著dict_sys->mutex我們還可以發現有以下幾個操作,若發生在session2,都會被阻塞

1)                 1) flush tables

2)                    select * from information_schema.tables;

2) 以上兩個因為都要訪問到表物件列表,還比較好理解

3)                 select * from information_schema.innodb_sys_tables;

3)實際上可以用另外乙個鎖來單獨處理sys_tables

4)                  show create table another_table

這個是因為必須判斷是否有外來鍵關聯

簡單留個問題:為什麼show tables並不會被阻塞?

關於MySQL建表對DML的影響

今天一位同學問到線上曾經碰到過連續建表,導致阻塞普通的 insert update 等。不過也沒有保留現場。因此有疑問為什麼建表會影響 dml?分析 首先這個現象不是在所有場景都會碰到 否則 mysql 的使用者們早就跳起來了 一來建表這個操作本身很快,只涉及到寫表定義檔案和初始化表空間。中間涉及到...

建表mysql語句嗎 關於MySQL語句建表的總結

在寫 之前,需要注意的乙個問題是,使用命令列模式寫 mysql 語句,如果涉及到中文,最好利用 mysql charset gbk 命令將客戶端字符集設定為 gbk,這樣能保證正確插入和讀 取中文資料庫端字符集可以是 gb2312,gbk,utf8 等支援中文的字符集 如果是利用 mysql 提供的...

mysql 建表原則 MySql基本的建表原則

1.定長和變長的分離 如int,char,time所佔位元組是固定的字段放在一張表 如varchar,text所佔位元組不確定的字段放在一張表中 2.常用字段和不常用字段進行分離,根據查詢頻率來設計 3.一對多的關聯表可以新增冗餘字段,如商品分類表 和商品表 在首頁中需要顯示每個分類商品總數.解決方...