WAL 卡住了
昨天在 staging 查一台 Windows Gateway,明明服務還能回應,但磁碟空間慢慢少掉。第一眼看 log 沒有明顯 error,重啟後空間又回來,這種最危險,因為很容易被當成偶發狀況。
最後我把 SQLite 的 WAL 和 checkpoint 狀態一起拉出來看,才發現問題不是寫入量大,而是有一個 worker 的交易停在跨執行緒的等待點。它沒有 timeout,也沒有被正確喚醒。交易一直沒結束,checkpoint 就沒有辦法往前走。
這個在 production 要注意,因為監控只看 process alive 或 API 能回 200 完全不夠。服務看起來正常,不代表資料庫正在健康地收斂。重啟確實能暫時把 WAL 吃回去,但那只是把現場清掉,沒有回答為什麼它會卡住。
我現在在升級後會多看三個數字:WAL 檔案大小、checkpoint 連續失敗次數、最後一次成功 checkpoint 的時間。如果 WAL 持續長大,同時最後成功時間停住,就先把它當成交易沒有收尾來查,不會先做一輪重啟。
另外一個坑是診斷資訊可能顯示沒有 active reader,但 checkpoint 仍然被卡住。worker 卡在等待時,不一定會把自己的狀態回報出來,所以空清單不等於沒有 blocker。
實測結果是,涉及 worker handoff 的 transaction 都要有 deadline,也要能 rollback。自動化最怕的不是報錯,而是安靜地卡住,然後等你幾天後才從磁碟告警發現。
作者:Bo-Han Chen