解決 Docker 官方的 MySQL 8 執行 INSERT 超級慢的問題
原本 insert 20 筆資料會耗時 1秒,改完後,insert 500 筆不到 0.1 秒!
注意事項
- 雖然以下不會執行sql語法,但動到資料庫參數,要確認隨時可以回復到可用狀態。
- 如果已有 my.cnf 檔,就建立另一個檔
環境
- 官方的 MySQL 8.4 Docker image (
FROM mysql:8
)
解法
加入一個自定義 my.cnf 檔在 /etc/mysql/conf.d/ ,內容:
[mysqld]
# 通常設定為系統 RAM 的 60-80%。這裡數值約16G
innodb_buffer_pool_size = 17089934592
# 增大此緩衝區可以提高寫入性能,特別是在處理大量寫入時,會減少磁碟寫入的頻率。
# 這裡數值約256MB
innodb_log_buffer_size = 268217728
# 是否在每個事務提交後同步二進制日誌(Binary Log)。
# 設置為 1 會增加每個事務的成本,設為 0 或 100 可以提高寫入性能。
sync_binlog = 0
# 事務提交時,何時將日誌寫入磁碟的選項。設為 0 可以減少事務提交的 I/O 負擔,
# 但會犧牲持久性,可能遺失最近 1 秒內的事務記錄。
innodb_flush_log_at_trx_commit = 0
# 停用二進制日誌(Binary Log)
skip-log-bin = 0
References
以下僅為測試數據
用以下參數,insert 500 筆的時間: 0 分 10.40642 秒
[mysqld]
innodb_buffer_pool_size = 17089934592
innodb_log_buffer_size = 268217728
# sync_binlog = 0
innodb_flush_log_at_trx_commit = 0
skip-log-bin = 0
用以下參數,insert 500 筆的時間: 0 分 11.31482 秒
[mysqld]
innodb_buffer_pool_size = 17089934592
innodb_log_buffer_size = 268217728
sync_binlog = 0
# innodb_flush_log_at_trx_commit = 0
skip-log-bin = 0
用以下參數,insert 500 筆的時間: 0 分 0.06932 秒
[mysqld]
innodb_buffer_pool_size = 17089934592
innodb_log_buffer_size = 268217728
sync_binlog = 0
innodb_flush_log_at_trx_commit = 0
# skip-log-bin = 0
用以下參數,insert 500 筆的時間: 0 分 0.07774 秒
[mysqld]
innodb_buffer_pool_size = 17089934592
innodb_log_buffer_size = 268217728
sync_binlog = 0
innodb_flush_log_at_trx_commit = 0
skip-log-bin = 0
留言
張貼留言