mysql臨時表,臨時表空間,ibtmp1表空間暴增原因初探
問題的形式解答:
一、MySQL在什麼情況下會建立臨時表(Internal Temporary Table Use in MySQL)?
我列舉3個
1. UNION查詢;
2. insert into select ...from ...
3. ORDER BY和GROUP BY的子句不一樣時;
4.資料表中包含blob/text列
等等,其實還有好多。具體參考 https://dev.mysql.com/doc/refman/5.7/en/internal-temporary-tables.html
二、怎麼知道mysql用了臨時表呢?
這個問題很簡單, EXPLAIN 檢視執行計劃結果的 Extra 列中,如果包含 Using Temporary 就表示會用到臨時表。舉個例子,有個感性認識。
建立測試表t22 :create table t22 as select * from information_schema.tables;
mysql> desc t22; +-----------------+---------------------+------+-----+---------+-------+ | Field | Type | Null | Key | Default | Extra | +-----------------+---------------------+------+-----+---------+-------+ | TABLE_CATALOG | varchar(512) | NO | | | | | TABLE_SCHEMA | varchar(64) | NO | | | | | TABLE_NAME | varchar(64) | NO | | | | | TABLE_TYPE | varchar(64) | NO | | | | | ENGINE | varchar(64) | YES | | NULL | | | VERSION | bigint(21) unsigned | YES | | NULL | | | ROW_FORMAT | varchar(10) | YES | | NULL | | | TABLE_ROWS | bigint(21) unsigned | YES | | NULL | | | AVG_ROW_LENGTH | bigint(21) unsigned | YES | | NULL | | | DATA_LENGTH | bigint(21) unsigned | YES | | NULL | | | MAX_DATA_LENGTH | bigint(21) unsigned | YES | | NULL | | | INDEX_LENGTH | bigint(21) unsigned | YES | | NULL | | | DATA_FREE | bigint(21) unsigned | YES | | NULL | | | AUTO_INCREMENT | bigint(21) unsigned | YES | | NULL | | | CREATE_TIME | datetime | YES | | NULL | | | UPDATE_TIME | datetime | YES | | NULL | | | CHECK_TIME | datetime | YES | | NULL | | | TABLE_COLLATION | varchar(32) | YES | | NULL | | | CHECKSUM | bigint(21) unsigned | YES | | NULL | | | CREATE_OPTIONS | varchar(255) | YES | | NULL | | | TABLE_COMMENT | varchar(2048) | NO | | | | +-----------------+---------------------+------+-----+---------+-------+ 21 rows in set (0.02 sec) mysql> explain -> select table_schema ,table_name, create_time from t22 where table_schema like 'test%' -> union -> select table_schema ,table_name, create_time from t22 where table_schema like 'information%' -> ; +----+--------------+------------+------------+------+---------------+------+---------+------+----------+----------+-----------------+ | id | select_type | table | partitions | type | possible_keys | key | key_len | ref | rows | filtered | Extra | +----+--------------+------------+------------+------+---------------+------+---------+------+----------+----------+-----------------+ | 1 | PRIMARY | t22 | NULL | ALL | NULL | NULL | NULL | NULL | 12522369 | 11.11 | Using where | | 2 | UNION | t22 | NULL | ALL | NULL | NULL | NULL | NULL | 12522369 | 11.11 | Using where | | NULL | UNION RESULT | <union1,2> | NULL | ALL | NULL | NULL | NULL | NULL | NULL | NULL | Using temporary | +----+--------------+------------+------------+------+---------------+------+---------+------+----------+----------+-----------------+ 3 rows in set, 1 warning (0.02 sec)
三、臨時表有關的引數有哪些?
innodb_temp_data_file_path = ibtmp1:12M:autoextend
tmp_table_size = 16777216
max_heap_table_size =16777216
default_tmp_storage_engine=InnoDB
internal_tmp_disk_storage_engine= InnoDB
四、mysql臨時表配置引數是tmp_table_size,當臨時表空間不夠用的時候怎麼辦?
如果臨時表中需要儲存的資料量超過了上限( tmp-table-size 或 max-heap-table-size 中取其大者),這時候就需要生成基於磁碟的臨時表了。也就是放在innodb_temp_data_file_path指定的臨時表空間中。
如果你對這句話有疑問,那我舉個例子來看下:反覆執行語句: insert into t22 select * from t22; 同時檢視錶空間ibtmp1的大小變化。反覆執行insert 語句,插入表中的數量指數級增長。
看下例子:
五、看圖說話,做了上個實驗,不知道你是否會有如下想法:既然內部臨時表(Internal Temporary Table)用於排序,分組,當需要的儲存空間超過 tmp-table-size 上限的時候,使用臨時表空間。臨時表空間是磁碟,速度比不上記憶體,那是不是可以加大tmp_table_size來優化需要使用臨時表的SQL語句?
當然可以呀,tmp_table_size最大值是18446744073709551615,如果建議256M。
六、mysql中是如何監控臨時表和臨時表空間使用情況的?
mysql> show status like '%tmp%'; +-------------------------+-------+ | Variable_name | Value | +-------------------------+-------+ | Created_tmp_disk_tables | 1 | | Created_tmp_files | 7 | | Created_tmp_tables | 18 | +-------------------------+-------+
建議Created_tmp_disk_tables/Created_tmp_tables不要超過25%。如果Created_tmp_disk_tables數量很大,檢視是否有很多慢sql,是否有很多使用臨時表的語句。加大
tmp_table_size
的值。
七、mysql的臨時表空間檔案暴增,可以達到幾百G,你認為形成的原因是什麼?
第四個問題做的例子,如果你不停的反覆的實驗,你會發現ibtmp1增長的速度驚人。有個專案,曾經ibtmp1暴增到300G。一看慢sql日誌,有大量慢sql,而且有很多語句需要排序。所以給ibtmp1加上限制最大值。innodb_temp_data_file_path = ibtmp1:12M:autoextend:max:5G,mysql會反覆利用。
參考:老葉茶館
https://mp.weixin.qq.com/s?__biz=MjM5NzAzMTY4NQ==&mid=207355450&idx=3&sn=3e3a2c0a7497a8cd099ddc5c33a9932d&scene=21#wechat_redirect
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/30393770/viewspace-2638834/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- MySQL InnoDB臨時表空間配置MySql
- Oracle臨時表空間檢視、新增臨時表空間資料檔案、修改預設臨時表空間 方法!Oracle
- 消除臨時表空間暴漲的方法
- MySQL 5.7 新特性 共享臨時表空間及臨時表改進MySql
- oracle臨時表空間相關Oracle
- 4.2.1.8規劃臨時表空間
- 刪除臨時表空間組
- oracle 臨時表空間的增刪改查Oracle
- 臨時表空間被佔滿的原因查詢
- MYSQL造資料佔用臨時表空間MySql
- oracle建立臨時表空間和資料表空間以及刪除Oracle
- 臨時表空間和回滾表空間使用率查詢
- 2.5.7 建立預設臨時表空間
- SQLServer如何釋放tempdb臨時表空間SQLServer
- oracle11g 查詢臨時表空間的使用率和正在使用臨時表空間的使用者Oracle
- 臨時表空間ORA-1652問題解決
- oracle建立使用者,表空間,臨時表空間,分配許可權步驟詳解Oracle
- 檢視oracle臨時表空間佔用率的檢視Oracle
- MySQL臨時表MySql
- 臨時表空間使用率過高的解決辦法
- Oracle 12C RMAN備份佔用大量臨時表空間Oracle
- dbms_lob儲存過程導致臨時表空間100%儲存過程
- 16、表空間 建立表空間
- MySQL之臨時表MySql
- mysql 建立臨時表MySql
- 12C關於CDB、PDB 臨時temp表空間的總結
- 查詢過去一段時間內某條sql使用的臨時表空間大小SQL
- 萬萬沒想到,我在夜市地攤解決了MySQL臨時表空間難題~~MySql
- 當使用者無限制使用表空間配額且表空間有足夠空間時出現超出表空間的空間限額
- MySQL 中的臨時表MySql
- MySQL InnoDB表空間加密MySql加密
- MySQL 傳輸表空間MySql
- Oracle 查詢佔用臨時表空間大的歷史會話和SQLOracle會話SQL
- MySQL 中的共享表空間與獨立表空間如何選擇MySql
- PostgreSQL:臨時表SQL
- mysql之 表空間傳輸MySql
- mysql收縮共享表空間MySql
- MySQL InnoDB Undo表空間配置MySql