Transaction-Log

alter table alter column 導致大量日誌和數據文件增長

  • August 27, 2020

我有一個包含 2.6B 行的表,我需要將一列從 Char(1) 更改為 Varchar(64)。該表超過 300GB,有幾個索引。該列可以為空,所以我正在執行的事務是:

ALTER TABLE XXXX ALTER COLUMN YYYYY varchar(64) NULL

我知道這是一個記錄操作,所以我將事務日誌的大小預先設置為 300GB,認為這已經足夠了,尤其是每 5 分鐘備份一次日誌以允許日誌空間重用。由於驅動器空間問題,在我不得不取消交易之前,交易日誌增長到 812GB。

我還經歷了數據文件 USED 大小的大幅增加,我不知道為什麼會這樣。使用的數據文件大小正好在 200GB 左右(在這個數據庫中完成的事務非常少,所以我知道增加來自這個 alter table 命令)。

我有一些疑問:

  1. 為什麼只是從 char(1) 更改為 varchar(64) 時數據文件會增加?我的印像是,這不應該改變儲存的數據量,除非自 varchar 以來實際需要該空間。由於 char(1) 是現有數據類型,所有現有值要麼為空,要麼為 1 字節,無需擴展現有數據。
  2. 在試圖弄清楚如何更好地做到這一點時,我從 Aaron Bertrand 那裡得到了這個答案,它似乎也適用於我的情況。這會是完成這項任務的更好方法嗎?
  3. 該數據庫位於 2 節點同步送出 AG 中,我注意到 redo_queue_size 超過 130GB,這意味著主數據庫發送日誌數據的速度比輔助數據庫應用它們的速度更快。這意味著當日誌備份完成時,主節點上的日誌無法截斷。這是這樣的正常行為嗎?alter column 語句是否作為一個大事務處理?如果是這樣,那將解釋為什麼日誌不斷增長。
  1. 我認為 VARCHAR 的最小儲存空間為 4 個字節,因此您確實將列的大小從 1 個字節更改為至少 4 個字節,導致(如您所見)隨著列的增長和其他周圍的東西。
  2. 我會推薦 Aaron 的方法作為實現相同目的的更快方法。它的缺點是不保留列順序….但是由於我們應該始終(大聲笑)使用命名列進行選擇和插入,因此儲存順序無關緊要。(可能需要刷新框架……)
  3. 你是對的。DDL 是一個記錄的事務,因此您在日誌文件/AG 執行狀況中觀察到的行為是可以預料的。

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