MongoDB 效能最佳化除了程式碼和資料函式庫設計外,伺服器組態的調校也至關重要。本文將探討如何監控伺服器資源,包括 CPU、記憶體、網路和磁碟 IO,並提供最佳化建議。首先要確保主機資源充足,再來是正確組態記憶體以減少 IO 需求,並最佳化磁碟 IO 與叢集組態。Linux 系統下,topuptimevmstatiostatnetstatbwm-ng 等指令是監控主機資源的利器。Windows 系統則可使用資源監視器和 PowerShell 的 Get-Counter 指令。MongoDB 的效能監控可以使用 db.serverStatus() 指令、MongoDB Compass、免費監控服務、Ops Manager 或 Atlas 等工具,第三方工具如 Percona、Datadog 和 SolarWinds 也提供更進階的功能。網路延遲的最佳化,可以考慮將應用程式佈署在靠近資料函式庫伺服器的位置,並減少應用程式的網路往返次數。CPU 效能則需要監控執行佇列長度,並透過最佳化查詢和索引來降低 CPU 負載。記憶體管理方面,WiredTiger 儲存引擎的快取大小是關鍵指標,可以使用程式碼片段取得相關資訊。系統的記憶體使用情況則可透過 vmstat (Linux) 或 systeminfo (Windows) 指令來監控,避免記憶體不足導致效能瓶頸。

伺服器監控與效能調校

在前面的章節中,我們探討瞭如何透過最佳化應用程式碼和資料函式庫設計來管理效能。在理想情況下,我們會從最佳化應用程式開始,使MongoDB的工作更高效,而不是增加其負擔。透過最佳化我們的schema、應用程式碼和索引,我們可以減少MongoDB為完成任務所需的工作量。

然而,在某些情況下,我們可能已經完成了所有實際的應用程式調校。此外,在使用第三方應用程式時,我們可能無法對應用程式碼進行任何修改。

現在是時候關注伺服器組態,確保它針對應用程式工作負載進行了最佳化。伺服器端的調校通常分為四個階段:

  • 確保伺服器主機上有足夠的記憶體和CPU來支援工作負載
  • 確保有足夠且正確組態的記憶體以減少IO需求
  • 最佳化磁碟IO,以確保磁碟請求在沒有過多延遲的情況下傳回
  • 確保叢集組態已最佳化,以避免叢集協調中的延遲並最大化叢集資源

主機層級監控

所有的MongoDB伺服器都在某個作業系統內執行,而該作業系統又託管在某個硬體平台上。在當今虛擬機器、容器和雲端基礎設施的世界中,硬體拓撲可能會被遮蔽。但是,即使無法直接觀察底層硬體,也可以觀察提供原始資源以支援MongoDB伺服器的作業系統容器。

在最基本的層面上,作業系統提供了四種基本資源:

  • 網路頻寬,允許資料在機器之間傳輸
  • CPU,允許執行程式碼
  • 記憶體,允許快速存取暫時性資料
  • 磁碟IO,允許大量資料被永久儲存

有多種工具可以幫助您監控主機利用率,包括商業和免費工具。在我們的經驗中,瞭解如何使用內建的效能工具是最佳的,因為這些工具始終可用。

在Linux上,您應該熟悉以下命令:

  • top
  • uptime
  • vmstat
  • iostat
  • netstat
  • bwm-ng

在Windows上,您可以使用資源監視器應用程式進行圖形檢視,並從PowerShell Get-Counter命令取得原始統計資料。

Linux 監控工具詳解

Linux提供了多種強大的命令列工具來監控系統效能。以下是一些常用的工具及其用途:

  • top 命令

    top 命令提供了系統目前執行的程式的動態實時檢視。它顯示了CPU使用率、記憶體使用率等資訊。

  • uptime 命令

    uptime 命令顯示了系統已經執行的時間、目前登入的使用者數量以及系統的負載平均值。

  • vmstat 命令

    vmstat 命令提供了關於系統虛擬記憶體、程式、CPU活動等的統計資訊。

  • iostat 命令

    iostat 命令用於監視系統輸入/輸出裝置負載,報告CPU使用率和磁碟I/O統計。

  • netstat 命令

    netstat 命令顯示了各種網路相關的資訊,如網路連線、路由表等。

Windows 監控工具詳解

在Windows上,您可以使用以下工具來監控系統效能:

  • 資源監視器

    資源監視器提供了一個圖形介面,用於監視CPU、磁碟、網路和記憶體的使用情況。

  • PowerShell Get-Counter 命令

    Get-Counter 命令用於取得效能計數器資料,可以用來監視系統的各種效能指標。

監控工具的最佳實踐

無論是在Linux還是Windows上,使用內建的效能工具都是監控系統資源利用率的最佳實踐。這些工具總是可用的,並且能夠提供有關系統資源利用率的詳細資訊。

使用 Plantuml 圖表呈現監控架構

此圖示展示了主機層級的資源及其對應的監控工具。在實際操作中,可以根據具體需求選擇合適的工具來監控相應的資源。

內容解密:

此Plantuml圖表呈現了主機資源及其對應的監控工具之間的關係。從主機出發,分別連線到CPU、記憶體、磁碟IO和網路頻寬。然後,每種資源進一步與其對應的監控工具相連,如CPU與top命令,記憶體與vmstat命令等。這種視覺化的呈現方式有助於理解不同資源與其監控工具之間的關聯。

伺服器監控:網路與CPU效能分析

網路效能對MongoDB的影響

網路在MongoDB的運作中扮演著至關重要的角色,負責將資料從伺服器傳輸到應用程式,以及在叢集內的各伺服器之間傳輸資料。網路延遲和頻寬直接影響資料函式庫的整體效能。

網路介面卡的瓶頸分析

現代伺服器的網路介面通常採用10GbE或100GbE網路卡,這些高速網路卡通常不會成為資料傳輸的瓶頸。然而,在舊式伺服器中,如果使用較低頻寬的網路卡(如1GbE),升級網路卡可以顯著提升資料傳輸效率。

使用bwm-ng指令可以監控網路介面的流量:

bwm-ng v0.6.2 (probing every 5.200s), press 'h' for help
input: /proc/net/dev type: rate
iface Rx Tx Total
=================================================================
lo: 0.00 B/s 0.00 B/s 0.00 B/s
eth0: 173.52 KB/s 8.84 MB/s 9.01 MB/s
virbr0: 0.00 B/s 0.00 B/s 0.00 B/s
---
-
---
-
---
-
---
-
---
-
---
-
---
-
---
-
---
-
---
-
---
-
---
-
---
-
---
-
---
-
---
--
total: 173.52 KB/s 8.84 MB/s 9.01 MB/s

網路延遲的測量與最佳化

網路延遲是影響MongoDB效能的重要因素。使用pingtraceroute指令可以測量客戶端與伺服器之間的網路延遲:

$ traceroute mongors01.eastasia.cloudapp.azure.com --port=27017 -T
traceroute to mongors01.eastasia.cloudapp.azure.com (23.100.91.199), 30 hops max, 60 byte packets
1 * * *
...
18 * * 23.100.91.199 (23.100.91.199) 118.392 ms

執行簡單的MongoDB命令(如rs.isMaster())可以測量實際的網路延遲:

mongo> var start=new Date();
mongo> var isMaster=rs.isMaster();
mongo> print ('Elapsed time', (new Date())-start);
Elapsed time 316

網路延遲的最佳化策略

  1. 將應用程式佈署在靠近資料函式庫伺服器的位置:理想情況下,應用伺服器應與MongoDB伺服器位於同一區域、資料中心,甚至同一機架。
  2. 減少應用程式的網路往返次數:最佳化查詢和資料存取模式,減少不必要的網路通訊。

CPU效能對MongoDB的影響

CPU是MongoDB效能的另一個關鍵因素。當CPU使用率過高時,可能導致效能下降。

CPU使用率與執行佇列的關係

單純觀察CPU使用率並不足以評估CPU負載。執行佇列(run queue)或稱負載平均值(load average)更能反映系統的真實負載狀況。

@startuml
skinparam backgroundColor #FEFEFE
skinparam componentStyle rectangle

title MongoDB伺服器監控與效能調校

package "資料庫架構" {
    package "應用層" {
        component [連線池] as pool
        component [ORM 框架] as orm
    }

    package "資料庫引擎" {
        component [查詢解析器] as parser
        component [優化器] as optimizer
        component [執行引擎] as executor
    }

    package "儲存層" {
        database [主資料庫] as master
        database [讀取副本] as replica
        database [快取層] as cache
    }
}

pool --> orm : 管理連線
orm --> parser : SQL 查詢
parser --> optimizer : 解析樹
optimizer --> executor : 執行計畫
executor --> master : 寫入操作
executor --> replica : 讀取操作
cache --> executor : 快取命中

master --> replica : 資料同步

note right of cache
  Redis/Memcached
  減少資料庫負載
end note

@enduml

CPU效能監控指標

  1. 執行佇列(Run Queue):理想情況下,執行佇列不應超過CPU核心數量的兩倍。
  2. CPU使用率(CPU Percent Busy):當CPU使用率達到100%時,應關注執行佇列的變化。

最佳化建議

  • 監控執行佇列:確保執行佇列保持在合理範圍內(約為CPU核心數量的兩倍)。
  • 最佳化查詢和索引:減少不必要的計算和資料處理,降低CPU負載。
內容解密:
  1. 網路延遲是影響MongoDB效能的重要因素,最佳化網路組態和減少網路往返次數是關鍵。
  2. CPU執行佇列是評估系統負載的關鍵指標,應保持在合理範圍內。
  3. 現代伺服器的高速網路卡通常不是瓶頸,但舊式伺服器可能需要升級網路卡。
  4. 將應用程式佈署在靠近資料函式庫的位置,可以有效降低網路延遲。

MongoDB 伺服器監控

在最佳化 MongoDB 效能的過程中,伺服器監控是至關重要的一環。透過監控,我們可以即時瞭解伺服器的運作狀態,找出潛在的效能瓶頸,並採取相應的最佳化措施。

作業系統資源監控

在監控 MongoDB 伺服器之前,我們需要先了解作業系統層面的資源使用情況。作業系統為 MongoDB 提供了四種關鍵資源:網路、CPU、記憶體和磁碟 IO。

CPU 監控

CPU 是 MongoDB 伺服器的核心資源之一。過高的 CPU 使用率可能會導致效能下降。要監控 CPU 使用率,可以使用以下方法:

  • 在 Linux 系統上,使用 uptime 命令可以檢視 CPU 的負載平均值。
$ uptime
06:38:39 up 42 days ... load average: 12.77, 3.66, 1.37
  • 在 Windows 系統上,可以使用 PowerShell 的 Get-Counter 命令來檢視處理器佇列長度。
PS C:\Users\guy> Get-Counter '\System\Processor Queue Length' -MaxSamples 5

記憶體監控

記憶體是另一個重要的資源。MongoDB 通常會快取資料在記憶體中,以避免過多的磁碟 IO。要監控記憶體使用情況,可以參考第 11 章的內容。

磁碟 IO 監控

磁碟 IO 對 MongoDB 的效能有著至關重要的影響。第 12 章和第 13 章將探討磁碟 IO 的效能管理。

MongoDB 伺服器監控

要了解 MongoDB 伺服器的效能,我們需要使用一些特定的工具和命令。

db.serverStatus() 命令

db.serverStatus() 命令是取得 MongoDB 伺服器效能指標的主要來源。這個命令提供了豐富的資訊,但是需要一定的經驗來解讀。

Compass

MongoDB Compass 是 MongoDB 的官方 GUI 工具,提供了一個簡單易用的效能監控儀錶板。

免費監控

MongoDB 提供了一個簡單的免費監控服務,可以在雲端檢視 MongoDB 伺服器的效能指標。要啟用免費監控,可以執行 db.enableFreeMonitoring() 命令。

rsUser:PRIMARY> db.enableFreeMonitoring()
{
    "state" : "enabled",
    "message" : "To see your monitoring data, navigate to the unique URL below. Anyone you share the URL with will also be able to view this page. You can disable monitoring at any time by running db.disableFreeMonitoring().",
    "url" : "https://cloud.mongodb.com/freemonitoring/cluster/WZFEDJBMA23QISXQDEDXACFWGB2OWQ7H",
    "userReminder" : "",
    "ok" : 1,
    "operationTime" : Timestamp(1599995708, 1)
}

Ops Manager

MongoDB Ops Manager 是 MongoDB 的商業化管理平台,提供了一整套的管理、監控和自動化功能。

MongoDB Atlas

如果您使用的是 MongoDB Atlas,那麼您可以使用 Atlas 提供的圖形化監控介面。

第三方監控工具

除了官方提供的工具之外,還有很多第三方監控工具可以提供更豐富的功能,例如 Percona、Datadog 和 SolarWinds 等。

記憶體調校

在前面的章節中,我們探討了減少MongoDB伺服器工作負載需求的技術。我們考慮了結構化和索引資料集的選項,以及調校MongoDB請求,以最小化處理工作請求所需的資料量。也許80%的效能提升來自於這些應用層級的最佳化。

然而,在某一點上,我們的應用程式架構和程式碼已經盡可能地最佳化,而我們對MongoDB伺服器提出的需求是合理的。現在,我們的首要任務是確保MongoDB能夠快速回應我們的請求。當我們向MongoDB傳送資料請求時,最關鍵的因素是資料是否在記憶體中,還是需要從磁碟中擷取。

與所有資料函式庫一樣,MongoDB使用記憶體來避免磁碟I/O。從記憶體讀取通常需要約20奈秒,而從非常快的固態硬碟硬碟讀取需要約25微秒——慢了1000倍。從磁性硬碟讀取可能需要4-10毫秒——又慢了2000倍!因此,MongoDB——與所有資料函式庫一樣——被設計成盡可能避免磁碟I/O。

MongoDB記憶體架構

MongoDB支援多種可插拔的儲存引擎,每種引擎都以不同的方式使用記憶體。事實上,甚至有一種記憶體儲存引擎,只將活動資料儲存在記憶體中。然而,在本章中,我們將只關注預設的WiredTiger儲存引擎。

當使用WiredTiger儲存引擎時,MongoDB消耗的大部分記憶體通常是WiredTiger快取。

function memory() {
    let serverStats = db.serverStatus();
    print('Mongod 虛擬記憶體 ', serverStats.mem.virtual);
    print('Mongod 常駐記憶體', serverStats.mem.resident);
    print(
        'WiredTiger 快取大小',
        Math.round(
            serverStats.wiredTiger.cache
                ['bytes currently in the cache'] / 1048576
        )
    );
}
memory();

內容解密:

  1. db.serverStatus():這個命令提供有關MongoDB伺服器狀態的詳細資訊,包括記憶體使用情況。
  2. serverStats.mem.virtual:顯示MongoDB分配的虛擬記憶體總量。
  3. serverStats.mem.resident:顯示目前分配給物理記憶體的記憶體量。
  4. serverStats.wiredTiger.cache['bytes currently in the cache']:顯示目前WiredTiger快取中使用的位元組數。

透過執行這個指令碼,我們可以獲得MongoDB記憶體使用情況的概覽,包括虛擬記憶體、常駐記憶體和WiredTiger快取大小。

主機記憶體

雖然組態MongoDB記憶體是一個大話題,但從作業系統的角度來看,記憶體管理非常簡單。要麼有可用的自由記憶體,一切正常,要麼沒有足夠的自由記憶體,事情就會變糟。

當實體自由記憶體耗盡時,嘗試分配記憶體會導致現有的記憶體分配被“交換”到磁碟。由於磁碟比記憶體慢數百倍,記憶體分配突然需要更長的時間來滿足。

測量記憶體

在Linux系統上,可以使用vmstat命令來顯示可用的記憶體:

$ vmstat -s
16398036 K total memory
10921928 K used memory
10847980 K active memory
3778780 K inactive memory
1002340 K free memory
4236 K buffer memory
4469532 K swap cache
0 K total swap
0 K used swap
0 K free swap

在Windows上,可以使用資源監視器應用程式或在PowerShell提示符下發出以下命令來測量記憶體:

PS C:\Users\guy> systeminfo | Select-string Memory

內容解密:

  1. vmstat -s:顯示系統的虛擬記憶體統計資訊。
  2. systeminfo | Select-string Memory:在Windows上查詢系統資訊中的記憶體相關資訊。

這些命令可以幫助我們瞭解系統的記憶體使用情況,包括總記憶體、已用記憶體、自由記憶體等。