Mysql

有什麼方法可以加快 MySQL 中一個非常大的表的分區的重組速度?

  • January 16, 2016

因此,我們有這個 1.5TB+ 的龐大表,其中包含數十億條記錄,在過去幾個月中一直被忽視,需要添加新的分區。分區基於按月創建的時間戳,最後一個分區是從 3 月開始的。所以我們在 pMax 分區中有大約 4 個月的數據,接近 700GB。這個表當然是業務關鍵的,我們不能有太多的停機時間。

我有一個較小的表,在 pMax 分區中大約有 80G,並且花了大約 6 個小時來重組和提取 13G 的數據一個月。因此,修好這張大桌子很容易需要大約 3 天的時間。

這就是我用來重組和添加分區的方法:

alter table db.table 
reorganize partition pMax 
into (partition p20150201 values less than ('2015-03-01'), 
partition p20150301 values less than ('2015-04-01'), 
partition pMax values less than (maxvalue));

創建具有為明年創建的分區的新表,然後從目前表插入數據並在完成後重命名會更快嗎?考慮到桌子的大小,我仍然認為這將永遠需要……但不知道我還有什麼其他選擇,如果有的話……

有沒有人使用 pt-online-schema-change 來重組分區?聽起來我應該可以線上完成.. 只需將我們的儲存空間增加一倍。

你可能想試試 Percona 的pt-online-schema-change

pt-online-schema-change 模擬 MySQL 在內部更改表的方式,但它適用於您希望更改的表的副本。這意味著原始表沒有被鎖定,客戶端可以繼續讀取和更改其中的數據。

pt-online-schema-change 通過創建要更改的表的空副本、根據需要對其進行修改,然後將原始表中的行複製到新表中來工作。複製完成後,它會移開原始表並用新表替換它。預設情況下,它還會刪除原始表。

數據複製過程是在小塊數據中執行的,這些數據塊會有所不同,以嘗試使它們在特定的時間內執行(請參閱–chunk-time)。此過程與其他工具(例如 pt-table-checksum)的工作方式非常相似。複製過程中對原表中數據的任何修改都會反映在新表中,因為該工具會在原表上創建觸發器以更新新表中的相應行。觸發器的使用意味著如果表上已經定義了任何觸發器,則該工具將無法工作。

當工具完成將數據複製到新表中時,它使用原子 RENAME TABLE 操作同時重命名原始表和新表。完成後,該工具會刪除原始表。

來源:https ://www.percona.com/doc/percona-toolkit/2.2/pt-online-schema-change.html

這不是一個完美的解決方案,但可能比 100% 停機更好:

製作一個腳本(bash/sql),首先將 db.table 重命名為 db.tableBig,然後立即重新創建 db.table。這將在瞬間發生,因此可以繼續插入到您的表中。

做你的重新分區。‘Alter table’ 或 ‘csv dump + load data’,我不知道什麼是最快的。對於轉儲/載入,首先使用正確的分區創建 tableNew,然後將 tableBig 的轉儲/載入到 tableNew:

$ echo "select * from db.tableBig" | mysql -u... > tableDump.csv
$ echo "load data local infile 'tableDump.csv' into table db.tableNew FIELDS TERMINATED BY '\t';" > importDump.sql
$ mysql --local-infile -u... < importDump.sql

(對於 3GB 的表,我花了大約 20 分鐘來轉儲和載入,對於 mysql 來說,比分區快得多,強度也更低。但是對於 700GB?)

分區後,再次使用腳本盡可能快地執行此操作: 1. 將表重命名為 tableNewData;2.將tableNew重命名為table;3. 插入表 select * from tableNewData。

  • 在此期間,您可以繼續收集數據。
  • 您可以對 tableBig 中的舊數據進行數據處理(不包括新數據)
  • 如有必要,您可以對新數據進行一些查找
  • (我不知道這在 1.5TB 表上是否可取,但是使用 UNION 來選擇新舊數據?)

我希望你能明白。我在 sql 和 bash 之間可能存在一些錯誤,所以請先在測試表上測試並查看 sql/bash。

引用自:https://dba.stackexchange.com/questions/106971