MySQL 5.1,Ubuntu 10.10 64bit,Linode虛擬機。Mysql更新性能突然降臨
所有表格均爲InnoDB。
我們的一臺生產機器使用包含31個相關表的MySQL數據庫。在一張表中,有一個字段包含顯示值,這些值可能會每天改變數次,具體取決於條件。
顯示值的這些更改將在使用時間內全天使用。腳本會定期運行並檢查一些可能導致更改的便宜條件,並在條件滿足時更新顯示值。然而,這種懶惰的方法並沒有捕捉到所有可能出現的應該更新顯示值的場景,以便在工作時間內將後臺處理負載降到最低。
每晚一次腳本清除存儲在表中的所有顯示值並重新計算它們,從而捕獲所有可能的更改。這是一個非常昂貴的操作。
這已經運行了大約6個月。突然,3天前,夜間劇本的運行時間從平均40秒降至11分鐘。
存儲數據的總體比例沒有顯着變化。
我已經調查儘可能最好,而突然運行較慢的腳本部分是寫入新顯示值的最後一條更新語句。每行執行一次,給定行(INT(11))id和新顯示值(也是INT)。
update `table` set `display_value` = ? where `id` = ?
有趣的是,之前的所有值的清洗是爲執行:
update `table` set `display_value` = null
而這個說法仍然以相同的速度運行,一如既往。
display_value
字段未編入索引。主鍵是id
。 table
中有4個其他外鍵在執行期間的任何時候都沒有修改。
最終曲線球:如果我將這個模式轉儲到測試虛擬機,並執行相同的腳本,它將在40秒內運行,而不是11分鐘。我沒有試圖在生產機器上重建模式,因爲這不是一個長期的解決方案,我想了解這裏發生了什麼。
我的索引有問題嗎?在同一行上進行數千次更新之後,它們是否會陷入其中?
更新
我能夠運行在最優化的模式,徹底解決了這個問題。由於InnoDB不支持優化,這迫使重建,並解決了這個問題。也許我的索引損壞了?
mysqlcheck -A -o -u <user> -p
經過上週末進一步的測試,我一直無法弄清楚的突然變化。與以前的歷史相比,這個腳本仍然需要很長時間才能執行。我甚至完全重新啓動了生產機器。 – 2011-04-24 13:11:32