MySQL瓶頸分析與優化

做者:蔣樂興mysql

簡介

經過sysbench的oltp_read_write測試來模擬業務壓力、以此來給指定的硬件環境配置一份比較合理的MySQL配置文件。ios

環境介紹
硬件配置
圖片描述sql

軟件環境
圖片描述數據庫

優化層級與指導思想

優化層級
MySQL數據庫優化能夠在多個不一樣的層級進行,常見的有:緩存

SQL優化
參數優化
架構優化 架構

本文重點關注:參數優化併發

指導思想
日誌先行 -- 一個事務可否成功提交的關鍵是日誌是否成功落盤,與數據沒有太大的關係;也就是說對寫的優化能夠表述爲各方面的資源向寫操做傾斜。
瓶頸分析 -- 經過show global status 的各個計數器的值基本上就能分析出當前瓶頸所在,再結合一些簡單的系統層面的監控工具如top iostat 就能明確瓶頸。
總體性能是「讀」&「寫」之間的再平衡。工具

優化過程

優化前
my.cnf中的內容(關鍵部分)
圖片描述
圖片描述
圖像地址:
http://www.sqlpy.com/mysqlz/t...性能

監控數據
show global status 中Innodb_data_pending_fsyncs 這個status比較高;
iostat的util項有比較明顯的波峯,峯值使用率高達85%;測試

監控數據分析與優化思路
對監控數據有兩種可能的解釋:
因爲最小化的安裝的buffer_pool_size比較小,因此會頻繁的觸發innodb_buffer_pool的最大髒頁的限制,使得innodb進入暴力刷盤的模式,這種狀況下io使用率會明顯上升。
redo日誌重用。 最終的影響多是二者的疊加,這裏先從buffer_pool開始優化。

優化緩衝池
my.cnf中的內容(關鍵部分)
圖片描述
圖片描述

圖像地址:
http://www.sqlpy.com/mysqlz/t...

監控數據
show global status 中Innodb_data_pending_fsyncs 這個status減少到了 1;
iostat的util項峯值有所降低;
從性能圖像能夠看出增大innodb_buffer_pool_size的值後、性能的峯值所對應的併發更高了(當innodb_buffer_pool_size默認的128M調整到200G時innodb_buffer_pool_instances自動增大到了8)

調整innodb_buffer_pool_size先後的性能對比
圖片描述

性能大概提升3倍

圖像地址:
http://www.sqlpy.com/mysqlz/t...

監控數據分析與優化思路
針對innob_buffer_pool_size的調整取得了必定的收穫,下面將要調整的就是針對redo重用的狀況了,也就是說咱們要增大innodb_log_files_in_group和innodb_log_file_size到一個合適的值。
innob_buffer_pool_size取得的收穫還能夠進一步擴大,那就是增大innodb_buffer_pool_instances的值。

優化日誌文件
根據對以前測試的記錄每完成一組測試LSN增大4.5G、測試持續時間大概是5分鐘;理論上把redo文件增大到5G能夠作到整個測試的過程當中不發生日誌重用、這樣的話測試的跑分會更高、曲也線更平滑,不過這個會影響數據庫宕機恢復的時間。MySQL在默認配置下innodb_log_files_in_group=2,innodb_log_file_size=48M也就是說跑完一組測試redo日誌要刷新48輪(1024*4.5/96 ==48) 先看一下把日誌刷新減小到9輪的狀況。

my.cnf中的內容(關鍵部分)
圖片描述
圖片描述

圖像地址:
http://www.sqlpy.com/mysqlz/t...

調整innodb_log_files_in_group&innodb_log_file_size先後的性能對比
圖片描述

性能大概提升2倍

圖像地址:
http://www.sqlpy.com/mysqlz/t...

如今看一下日誌重用控制在一輪(5G)以內的性能表現

my.cnf中的內容(關鍵部分)
圖片描述
圖片描述

圖像地址:
http://www.sqlpy.com/mysqlz/t...

調整innodb_log_files_in_group&innodb_log_file_size先後的性能對比
圖片描述

性能大概提升2倍

圖像地址:
http://www.sqlpy.com/mysqlz/t...

監控數據分析與優化思路
1.增大redo到5G的狀況下因爲整個測試過程當中幾乎沒有日誌文件重用的問題,這樣也就規避由些引起的大量數據刷盤行爲,因此性能曲線也就更平滑了。
2.經過show global status 發現Table_open_cache_overflows=200W+、Thread_created=2k+
3.%Cpus : 80.5 us, 13.8 sy, 0.0 ni, 5.4 id, 0.0 wa, 0.0 hi, 0.3 si, 0.0 st 95%的使用率cpu資源成了大問題,這個使用率下能調整的參數很少了
4.對磁盤的監控數據代表util的峯值已經降低到14%、磁盤已經不在是問題;因此針對innodb_buffer_pool_size、innodb_log_files_in_group&innodb_log_file_size 這兩次優化的進入一步優化innodb_buffer_pool_instances、innodb_log_buffer_size 先不進行;在些採用「抓大放小」的方式先調整表緩存與線程緩存。

優化其它已知項
cpu使用率達到了95%,看到這個數值有一種發自心裏的無力感,因此打算所目前status中能明確的一些問題直接一塊兒調整了;增大table_open_cache&table_open_cache_instances用於優化表緩存、增大thread_cache_size使cpu不用頻繁的建立銷燬線程。

my.cnf中的內容(關鍵部分)
圖片描述
圖片描述

圖像地址:
http://www.sqlpy.com/mysqlz/t...

調整先後的比較
圖片描述
圖像地址:
http://www.sqlpy.com/mysqlz/t...

總結

1、考慮到cpu使用率已經達到95%且增長物理cpu不現實的狀況下,決定MySQL參數優化到此爲止;最後來看一眼此次優化成果。
圖片描述
圖像地址:
http://www.sqlpy.com/mysqlz/t...

2、前面因爲篇幅只給出配置文件的一部分、如今咱們來看一下完整的配置文件。
圖片描述
圖片描述
圖片描述
圖片描述

說明
1.之因此max_prepared_stmt_count要調整到這麼是由於sysbench的oltp_read_write這個測試會用於prepare語句、若是這個值不夠大的話咱們測試不了800+併發,你測試sysbench其它oltp用例可能不用這麼作,同理max_connections的配置也是如此(不過它確實設置的大了點)

2.有些參數在優化過程當中我並無調整主要緣由有兩個:①.這是有方法論指導的優化、它更像定向爆破,因此沒用的我不去動、在關鍵參數上調整後已經解決問題的狀況下,其它相關的參數我更加傾向不動。②.對於從show global status 中能看出很是明確指向的我也會採起多個參數一塊兒調整的策略。

相關文章
相關標籤/搜索