MySQL如何管理客戶端鏈接?線程池篇

MySQL如何管理客戶端鏈接?線程池篇

在以前的文章裏,爲你們介紹了MySQL的鏈接管理線程的工做方式,在這一篇裏爲你們介紹管理鏈接的第二種方式,線程池。緩存

MySQL默認的鏈接控制方式採用的是每一個鏈接使用一個線程執行客戶端的請求。MySQL的線程池是包含在企業版裏面的服務器插件。使用線程池的目的是爲了改善大量併發鏈接所帶來的性能降低。在大量併發鏈接的工做負載下,使用線程池能夠解決沒法利用CPU緩存、上下文切換開銷過大以及資源爭用等問題。服務器

線程池功能由插件庫文件、服務器系統變量及Performance Schema裏面的檢測點組成。併發

MySQL如何管理客戶端鏈接?線程池篇

線程池是由必定數量的線程組(默認爲16個經過thread_pool_size
進行配置)構成,每一個線程組管理一組客戶端鏈接,最大鏈接數爲4096。鏈接建立以後會以輪詢的方式分配給線程組。鏈接池打破了每一個鏈接與線程一一對應的關係,這一點與MySQL默認的線程控制方式不一樣,默認方式將一個線程與一個鏈接相關聯,以便給定的線程從其鏈接執行全部的語句。ide

默認狀況下,線程池試圖確保每一個組中每次最多執行一個線程,但有時爲了得到最佳性能,容許臨時執行多個線程。每組裏面有一個監聽線程,負責監聽分配給該組的鏈接。線程會選擇當即執行或稍後執行鏈接裏面的語句,若是語句是惟一接收到的,而且當前沒有排隊或正在執行的語句,該語句就會當即執行。其它狀況則會選擇稍後執行。當該語句被判斷爲當即執行時,監聽線程負責執行該語句,若是可以快速完成執行,該線程會返回監聽狀態,若是執行語句時間過長產生停滯,線程組會開啓一個新的監聽線程。線程池插件使用一個後臺線程監控線程組狀態,以確保線程組不會由於停滯的語句阻塞線程組。性能

能夠經過thread_pool_stall_limit 配置等待值時長,短等待值容許線程更快啓動,也有助於避免死鎖狀況。長時間等待值對於長時間運行的工做負載很是有用,能夠避免在當前語句執行時啓動太多新語句。插件

經過thread_pool_max_active_query_threads設置運行的最大線程,若是該值不爲0,則該數值爲容許運行的最大線程數量,設置爲0使用默認最大值。線程

線程池側重於限制短期運行語句的併發數量。在執行語句達到待值時長以前,它會阻止其餘語句開始執行。若是語句執行超過了待值時長,容許其繼續執行,但再也不阻止其餘語句啓動。經過這種方式,線程池嘗試確保每一個線程組中永遠不會有超過一個的短期運行語句,但可能有多個長時間運行的語句。設計

若是遇到磁盤I/O操做或用戶級鎖(行鎖或表鎖),語句就會被阻塞,將致使線程組沒法使用。線程池的回調功能,能夠確保線程池當即啓動該組中的新線程來執行另外一條語句。當一個被阻塞的線程返回時,線程池容許它當即從新啓動。orm

線程池包含兩個隊列,高優先級隊列和低優先級隊列。當前正在執行的語句及該事務後續關聯的語句將進入高優先級隊列,其它語句進入低優先級隊列。blog

此外,線程池重用活躍的線程,以更好地利用CPU緩存。這是一個對性能有很大影響的調整。

理論上,可能出現的最大線程數是 max_connectionsthread_pool_size的總和。當全部鏈接都處於執行模式,而且每一個組都建立了一個額外的線程來監聽,可能會發生這種狀況。

總結一下,MySQL的線程池被設計爲擴展鏈接、避免死鎖,經過對線程進行分組、區分優先級、輪詢調度,高效利用CPU緩存、減小上下文切換開銷,提高MySQL服務器性能!

相關文章
相關標籤/搜索