한국어English日本語简体中文繁體中文DeutschไทยTiếng ViệtРусскийPortuguês (Brasil)EspañolBahasa Indonesia

遊戲 Lag 白皮書 › L12 資料庫

連線池耗盡 Connection pool exhaustion

原因 ID db-pool · 主要負責 遊戲開發團隊(伺服器開發) · 協同 基礎設施團隊(DB 基礎設施)

在含圖解與實驗的完整版中開啟卡片 →

與 DB 建立的連線數是固定的,慢查詢占住連線時,其餘請求只能等待。

為什麼 慢查詢或請求暴增,使所有連線都在使用中 → 於是 新請求要等到有連線空出來 → 畫面上 登入時無限讀取、存檔變慢、逾時

症狀
連不上/無限讀取, 輸入延遲
因素
停滯, 延遲
誰會遇到
整個伺服器, 只有特定功能
何時
剛登入/維護剛結束, 人潮湧入時
負責單位
主要負責 遊戲開發團隊(伺服器開發) · 協同 基礎設施團隊(DB 基礎設施)
遊戲開發團隊要做的事
消除慢查詢、調整連線池大小與等待逾時(不要一味加大連線池)、依功能拆分連線池。
基礎設施團隊要做的事
確認 DB 的最大連線數與 CPU、IOPS 餘裕;擴充伺服器或自動擴展前,確認伺服器數 × 連線池大小在最大連線數以內;把連線等待與鎖等待指標加入監控。
數值參考
需要的連線數可用「每秒請求數 × 每筆請求占用連線的時間」估算。每秒 2,000 筆、每筆 5ms 時,平均隨時有 10 條連線在忙。考量請求湧入的情況,通常會準備兩三倍。查詢變慢到 150ms 時,同樣的請求量就需要 300 條。
圖表上
碰到上限後持平 · 使用中的 DB 連線數、連線等待時間
查看位置
在 DB 端依遊戲伺服器統計連線狀態。MySQL 看 SHOW PROCESSLIST 的 Host、Command(閒置連線為 Sleep)、Time,以及 Threads_connected、Threads_running 與被拒絕的連線數 Connection_errors_max_connections。PostgreSQL 把 pg_stat_activity 依 client_addr、state 分組統計。遊戲伺服器的連線池函式庫有輸出等待數與等待時間時,一併查看
符合的跡象
某台遊戲伺服器的連線達到連線池大小且全部都在執行查詢、閒置連線為 0 的期間,登入與存檔都在等待。或是 DB 的總連線數碰到 max_connections,新連線被拒絕
不符合的跡象
閒置連線充足卻仍然很慢時,是查詢本身的延遲(db-no-index、db-hot-row)或 DB 資源飽和的問題
確認方式
用基礎設施工具確認(不需要遊戲程式碼)
深入了解
一味加大連線池,只會增加 DB 的 CPU 負載與鎖定競爭,讓所有人一起變慢。此外,伺服器數 × 連線池大小超過 DB 的最大連線數時,新增或重新啟動的伺服器甚至無法建立連線。這在自動擴展或維護剛結束時很常見。

出處

  1. Number Of Database Connections PostgreSQL
    DB 資源用盡之後,增加連線反而會降低處理量;讓活躍連線數配合資源、其餘放進佇列,延遲與處理量都會比較好
  2. Too many connections MySQL
    max_connections 全部用完時,新連線會因 Too many connections 錯誤被拒絕
  3. Connections and Authentication (PostgreSQL Documentation) PostgreSQL
    max_connections:同時連線數上限,預設通常為 100
  4. SHOW PROCESSLIST Statement MySQL
    Host(用戶端位址)、Command(閒置 session 為 Sleep)、Time、State
  5. Server Status Variables MySQL
    Threads_connected、Threads_running、Connection_errors_max_connections(因達到 max_connections 而被拒絕的連線數)
  6. The Cumulative Statistics System (PostgreSQL Documentation) PostgreSQL
    pg_stat_activity:每條連線的 client_addr 與 state(active、idle、idle in transaction 等)

相關原因

同一層:L12 資料庫

同一症狀(連不上/無限讀取)在其他層的原因

查看含圖解與實驗的完整版卡片