天天看點

MySQL|空間碎片化問題處理

一、空間碎片化嚴重案例分享

1.1 問題描述

執行個體磁盤空間近1個月上漲趨勢明顯,主要是個别日志表存儲較大且部分表存在空間碎片化的現象。

1.2 處理流程

1、通過日常巡檢以及監控發現某執行個體磁盤空間近1月上漲趨勢明顯

MySQL|空間碎片化問題處理

2、在詢問業務方是否為正常的業務增長外,檢視該執行個體top表空間的表,排查是否存在異常較大的表

1)檢視資料存儲量較大的schema

SELECT table_Schema  , round(SUM((DATA_LENGTH + INDEX_LENGTH + DATA_FREE) / 1024 / 1024), 2) AS Total_Size FROM tables GROUP BY table_schema ORDER BY Total_Size DESC;           
MySQL|空間碎片化問題處理

2)檢視具體schema下top表的空間使用情況

SELECT table_schema, table_name  , round(DATA_LENGTH / 1024 / 1024, 2) AS Data_Size , round(INDEX_LENGTH / 1024 / 1024, 2) AS Index_Size , round(DATA_FREE / 1024 / 1024, 2) AS Free_Size FROM tables WHERE table_schema = 'db_rim' ORDER BY Data_Size DESC LIMIT 10;           
MySQL|空間碎片化問題處理

3、從以上截圖中我們可以得到資訊:db_rim庫庫下,rim_user_msg_log表的資料量很大,可檢視是否可對該表中無效的資料進行清理?rim_user_msg_analyse這張表的碎片化将盡17G,可考慮對這些碎片化空間進行回收

4、最終采取的處理方法為:rim_user_msg_log表直接清空,rim_user_msg_analyse進行碎片化回收

1)清理前

MySQL|空間碎片化問題處理

2)清理後

MySQL|空間碎片化問題處理

3)執行個體磁盤空間使用趨勢

MySQL|空間碎片化問題處理

二、表資料量過大清理案例

2.1 問題描述

通過對TOP表資料量的監控,我們可以看到sys_rest_server_log的資料量已經達到7000w,除空間占用外,我們更關注的是該表對資料庫帶來的性能隐患。若業務上或者人為不當的查詢該表資料,其操作的資源消耗在一定程度上一定會對正常業務造成影響。

MySQL|空間碎片化問題處理

2.2 問題處理

1、該表目前的表現主要有兩點,一點是某瞬時寫入量極大,另外一點是表日增可達到300w記錄數。對于資料庫而言這種表行為或業務設計是不合理的,我們需要搞清楚該表究竟是用來記錄哪些資訊,業務設計是否合理?

通過觀察表資料以及與相關開發人員溝通,我們得知該表會記錄應用端所有的接口調用資訊,我們所觀察到的資料增長尖峰也正是由于業務量上漲而導緻該表瞬間并發寫入大量日志資訊。

MySQL|空間碎片化問題處理
MySQL|空間碎片化問題處理

2、對于這種大資料量的日志記錄資訊,建議最好使用ELK這種日志分析服務,而不是使用資料庫進行存儲

3、限于開發人員開發能力有限,無法改造業務架構。針對該表日增長、瞬間增長都極大的情況,我們與開發人員溝通該表記錄的資料是否可從源端上進行減少。隻記錄重要資訊、非重要資訊的接口日志入庫進行屏蔽

4、确定表資料記錄可從最根本減産後,我們仍需要對目前7000w的資料進行處理,将曆史無效資料進行清理,并制定合适的資料清理政策

5、無效曆史資料清理/資料清理政策

1、建立備份表: create table sys_rest_server_log_bak_0228_1 like sys_rest_server_log;  
2、表名替換 将源表sys_rest_server_log重命名為備份表,備份表sys_rest_server_log_bak_0208_1重命名為源表sys_rest_server_log,業務資料會寫入空的新表,但是在rename期間這部分業務日志寫入會失敗【需關注】 rename table sys_rest_server_log to sys_rest_server_log_bak_0228_2,sys_rest_server_log_bak_0228_1 to sys_rest_server_log;  
3、将備份表sys_rest_server_log_bak_0208_2中的仍然需要的資料重新寫入到sys_rest_server_log,分批次寫入,sys_rest_server_log保留近15天資料。程式上可保證主鍵fd_id唯一,避免主鍵沖突。 insert into sys_rest_server_log select * from sys_rest_server_log_bak_0228_2 where fd_start_time between 'xxx' and 'xxx';  
4、調整平台資料清理政策,将服務運作日志備份天數改為15天,清除服務運作日志備份天數改為30天  
5、sys_rest_server_log_bak_0228_2表保留80+天記錄資料,暫時可以不做清理,等程式維護的sys_rest_server_log_backup有完備的資料後,将sys_rest_server_log_bak_0228_2表清除;           

三、總結歸納

2.1 如何判斷表碎片化問題是否嚴重

表資料的頻繁更新容易對表空間造成一定的碎片化,我們可以通過information_schema.table表中的data_free字段判斷該表碎片化是否嚴重。

2.2 如何處理碎片化問題

optimize table tableName; alter table tablName engine=innodb;           

2.3 大表曆史資料清楚過程中的關注點

1、通過建立bak表與源表進行rename替換,rename期間會造成業務對該表資料寫入失敗 
2、bak表建立的時需關注primayr key 
1)程式上保證主鍵唯一可不需要關注 
2)若主鍵使用自增長,建議在建立bak表建立時提高目前的auto_increment指,空餘一部分buffer空間,保證後續将源表曆史資料寫入rename後的新表時主鍵不沖突 
3、對于此類經常需要進行資料清理的表,建議使用分區表進行存儲,後續對資料的處理僅僅需要删除指定分區           

更多技術資訊請檢視雲掣官網

https://www.dtstack.com/dtsmart/