當我們的資料庫伺服器遇到如下的錯誤:ERROR: Too many connections 一種可能性就是我們的壓力確實很大,需要增加伺服器硬體資源或者增加資料庫伺服器。但是大多數情況下是我們的連接數配置不合理造成的。 在MySQL中,有如下幾個參數是和連接數配置相關的: Max_connectio ...
當我們的資料庫伺服器遇到如下的錯誤:ERROR: Too many connections
一種可能性就是我們的壓力確實很大,需要增加伺服器硬體資源或者增加資料庫伺服器。但是大多數情況下是我們的連接數配置不合理造成的。
在MySQL中,有如下幾個參數是和連接數配置相關的:
Max_connections
Max_used_connections
Connections
Max_user_connections
Back_log
Max_connect_errors
接下來我們逐一來分析這些參數的意義:
Max_connections:
是指整個資料庫伺服器所允許的最大連接數,可使用以下命令進行查詢:
Show variables like ‘max_connections’;
在Windows平臺該數值一般預設為151,如果超過該數值,由於限制那麼系統就會產生等待的情況,從而影響系統的併發量和吞吐量。
通常情況下,我們會根據伺服器的性能適當的調整一個合適的值,比如500-800,但是要註意該數值的最大值為16384,請不要超過這個值。
由於資料庫會為每個連接,分配一定記憶體資源和緩衝區,通常為每個連接分配256KB資源,所以設置要慎重一些,建議不要超過實際用戶的1.5倍。
在我們評估最大連接數數值的時候,我們可以使用以下的一些命令,來查看一下歷史數據,提供參考數據:
Show global status like ‘max_used_connection’;
這個命令用於查詢,伺服器自啟動以來運行期間的最大連接數。
show global status like 'Connections';
這個命令可以查詢伺服器自啟動以來的連接數的總數,這是一個累計值,可以查看資料庫連接的頻率。
通過檢測這些數據,我們就能得到是否需要增加Max_connections的證據。
如果max_used_connections 已經等於或者接近Max_connections,那麼我們就需要增加資料庫的最大值。
按照通用的20/80法則,我們建議留有20%的連接數用於系統備用,即Max_used_connections/Max_connections *100% < 80%。
按照經驗,我們會留比較大的連接數,比如留50%的連接數用於備用。
Max_user_connections
是指對每個用戶允許的最大連接數。
一般情況下我們都會讓其保持預設值,除非有特定的需要或者臨時性的用戶,我們才做出限制。
該參數會限制單個用戶的最大連接值,通常是對單用戶併發用戶進行限制。
Back_log
show variables like 'back_log';
該參數是用來緩存用戶連接的,相當於一個排隊的連接池。
在資料庫達到最大連接數的時候,新的連接請求會被存放在堆棧中,並等待其他連接釋放資源。
如果等待的連接數超過這個值,那麼新的連接將不會被接受。
這個數值不能超過系統的TCP/IP連接的監聽隊列數,否則無效。
Linux系統我們推薦設置為小於512的整數。
註意每個隊列會消耗256kb的記憶體資源。
Max_connect_errors
show variables like 'max_connect_errors';
該參數是指,當連接的錯誤數達到這個閾值的時候,系統會終止用戶的連接服務。
需要使用flush hosts來清除錯誤,否則就會報錯:
Host *** is blocked because of many connection errors.Unblock with ‘mysqladmin flush-hosts’.
當資料庫達到這個閾值的時候,資料庫認定系統出現了一個錯誤,並且會阻止該用戶後續的請求操作,除非使用命令刷新系統。
如果是內網環境,建議可以將數值設置的高一點,並使用任務機制定期刷新hosts。
Connect_timeout
show variables like '%connect_timeout%';
指定MySQL服務等待應答的時間,如果超時那麼客戶端會返回一個錯誤,bad handshake。
在Windows環境下預設值為10秒。
如果是區域網或者高併發的環境下,可以適當提高該數值,比如15-20 秒,以避免出現連接錯誤。
建議該數值要結合thread_cache_size建議適當提高該數值,以便提高更多的連接數。
Skip_name_resolve:
show variables like '%skip_name_resolve%';
該設置是用於提高資料庫伺服器的連接速度。
MySQL在獲得連接請求的時候,會根據請求中的IP地址,來反向查詢伺服器的主機名,然後再次獲取該伺服器的IP地址。
如果兩次獲取的IP地址一致,那麼才會建立連接。
按照這種設計,一次連接會耗費較長的時間,主要是一種安全上的驗證。
但是我們不推薦在廣域網環境下,打開這個設置,以防止黑客的攻擊。