Zabbix 5.0:服務端進程總結

Blog:部落格園 個人
參考:《深入理解Zabbix監控系統》、《Zabbix用戶手冊》

Zabbix服務端進程被分為不同的種類,每一種進程負責相應的任務,包括收集原始監控數據、對原始監控數據進行預處理、將預處理後的監控數據同步到資料庫、對監控數據進行計算以生成事件、計算和獲取內部監控數據,以及對資料庫中的數據進行清理等。

監控數據的收集進程

Zabbix伺服器的重要任務之一就是被動接收由Zabbix代理和各種Zabbix客戶端發送的監控數據,以及主動向Zabbix代理、Zabbix java gateway和Zabbix客戶端等數據源請求數據,其中被動接收數據由trapper類進程實現,主動請求數據則由poller類進程實現。

trapper類進程通過監聽TCP套接字來捕獲符合通訊協議的原始監控數據,poller類進程則使用ConfigCache作為輸入,根據快取資訊實現完善的任務調度。trapper類和poller類進程的下游是預處理進程,這兩類進程需要將收集到的原始監控數據發送到預處理進程。trapper類進程和poller類進程都會在進程內部維護一個靜態變數cached_message,用於暫存待發送的監控數據,並在各種必要的時機將該變數中的消息發送到預處理進程。

trapper類進程

Zabbix伺服器端的trapper進程負責接收來自Zabbix客戶端、Zabbix代理、zabbix_sender及其他外部進程發來的請求並進行處理,按照Zabbix 5.0的通訊協議規範,trapper進程只能接收JSON格式字元串的請求。

trapper進程由配置文件中的StartTrappers參數決定其啟動數量(允許啟動0~1000個進程,默認為5個)。

[root@prod-zabbix-server ~]# ps -ef|grep trapper
zabbix    8740  8643  0 Feb21 ?        01:55:26 /usr/sbin/zabbix_server: trapper #1 [processed data in 0.001288 sec, waiting for connection]
zabbix    8741  8643  0 Feb21 ?        01:13:24 /usr/sbin/zabbix_server: trapper #2 [processed data in 0.000863 sec, waiting for connection]
zabbix    8742  8643  0 Feb21 ?        01:02:48 /usr/sbin/zabbix_server: trapper #3 [processed data in 0.000664 sec, waiting for connection]
zabbix    8743  8643  0 Feb21 ?        01:55:36 /usr/sbin/zabbix_server: trapper #4 [processed data in 0.000788 sec, waiting for connection]
zabbix    8744  8643  0 Feb21 ?        01:43:59 /usr/sbin/zabbix_server: trapper #5 [processed data in 0.000802 sec, waiting for connection]

💡注意:至少要運行一個trapper進程用於在web前端展示伺服器可用性和隊列視圖。

總體而言,trapper進程所做的事情就是循環從TCP 套接字讀取請求消息,然後根據消息類型調用不同的函數進行處理,處理完畢後關閉該套接字連接。即每個循環處理一個請求,每個請求的處理都是在新的連接中進行通訊的。

數據處理:

  • 處理agent data和sender data請求:兩者處理過程類似,唯一區別是驗證過程,agent data要求監控項屬於主動客戶端(active agent)類型,而發送者數據(sender data)要求監控項屬於Zabbix trapper類型。請求的過程中,trapper進程的作用在於驗證數據的有效性,包括監控項狀態、監控項類型和主機狀態等。
  • 處理proxy config請求:將Zabbix伺服器的配置資訊傳輸到Zabbix代理。可以由Zabbix代理髮送到Zabbix伺服器(主動模式,默認),也可以由Zabbix伺服器發送到Zabbix代理(被動模式)。
  • 處理proxy data請求:可能由Zabbix伺服器或者被動模式下的Zabbix代理來處理。如果是Zabbix伺服器,說明它接收了一批來自Zabbix代理的監控值,此時需要將數據寫入快取或者進行LLD(Low-level discovery,自動發現)處理;如果是被動代理,說明它接收了Zabbix伺服器發送的數據請求,此時需要做的是將監控數據回復給Zabbix伺服器。從Zabbix 5.0開始,Zabbix代理具有了預處理的能力,所以proxy data中的監控值其實是已經預處理過的,不需要在Zabbix伺服器端再次預處理。
snmp trapper進程

snmp trapper進程由配置參數StartSNMPTrapper決定其啟動數量(允許0或1個進程),默認為0。該進程的工作方式是循環調用get_latest_data()和read_traps()函數,從trap文件(文件路徑由SNMPTrapperFile配置參數決定)中讀取數據,然後調用parse_traps()函數進行解析處理。

poller類進程

poller類進程是指以主動方式獲取原始監控數據的進程,包括poller進程、unreachable poller進程、ipmi manager/poller進程、icmp pinger進程、javapoller進程、proxy poller進程和http poller進程,一共有7種,它們各自負責採集不同類型的監控項數據。與trapper類進程不同的是,poller類進程需要自己執行監控數據採集邏輯,每一種監控項都需要調用不同的函數進行處理才能得到監控數據,而trapper類進程可以直接接收監控數據。從這個角度來說,對於同樣數量的監控任務,使用poller工作方式要比使用trapper工作方式的負載更高

工作機制

poller類進程首先需要解決的問題是如何調度數據採集過程,以保證大量數據採集任務的執行順序和間隔是正確且準確的。此外,每一種進程都並非唯一的,所以還要保證多進程之間的協調,避免衝突。Zabbix的解決方案是通過ConfigCache中定義的6個二叉堆結構來確定數據採集任務的執行順序和間隔。

多進程之間的衝突問題,解決方法是使用ConfigCache互斥鎖,即在訪問二叉堆之前加鎖,在訪問結束以後解鎖,從而保證同一時間只有一個進程在訪問。

poller進程

poller進程能夠處理除IPMI類型之外的所有監控項的數據採集,包括Zabbix客戶端(Zabbix agent)監控項、簡單檢查(Simple check)監控項、SNMP客戶端(SNMP agent)監控項、Zabbix內部(Zabbix internal)監控項、Zabbix聚合(Zabbix aggregate)監控項、外部檢查(External check)監控項、資料庫監視(Database monitor)監控項、HTTP客戶端(HTTP agent)監控項、SSH客戶端(SSH agent)監控項、TELNET客戶端(TELNET agent)監控項、JMX客戶端(JMX agent)監控項以及計算型(Calculated)監控項,共12種。

Zabbix客戶端監控項處理

poller進程對Zabbix客戶端(Zabbix agent)監控項進行處理的過程實際上就是以TCP套接字客戶端的身份與作為伺服器端的Zabbix客戶端進行通訊的過程。因此,當poller進程需要處理大量Zabbix客戶端監控項時,會同時與很多Zabbix客戶端建立TCP連接。(同一時刻每個進程最多建立一個連接,用後即關閉。)

unreachable poller進程

在網路通訊良好並且各方服務正常的情況下,poller進程所處理的Zabbix客戶端和SNMP客戶端監控項,以及IPMI進程處理的IPMI客戶端(IPMIagent)監控項和java poller進程處理的JMX監控項,都能夠成功執行並獲取監控數據。但是,當出現agent服務故障時,如果繼續由原來的poller類進程處理對應的監控項,大量的連接超時就有可能引起整體服務水平下降。unreachable poller進程就是對該問題的解決方案,當客戶端(包括Zabbix客戶端、SNMP客戶端、IPMI客戶端和JMX客戶端)服務不可用時,對應的監控項會轉移到unreachable poller隊列中處理。當unreachable poller進程發現某個客戶端已經恢復正常時,則將對應的監控項再轉移回原始隊列中。

一般情況下,由於大部分客戶端狀態是良好的,因此unreachable poller進程的負載並不高。但是,一旦發生大面積網路故障,會有大量監控項轉移到unreachablepoller進程的任務隊列中,此時進程的負載會飆升。如果要降低負載,可以考慮增加UnavailableDelay參數值,或者增加unreachable poller進程的啟動數量。

總結

Zabbix支援兩種收集監控數據的模式,在Zabbix伺服器端表現為同時存在trapper類進程和poller類進程。

trapper類進程用於被動接收來自Zabbix客戶端或者Zabbix代理的監控數據;poller類進程用於主動發起連接並向被監控對象請求監控數據。trapper類進程包括純trapper進程和snmp trapper進程,前者用於從Zabbix客戶端和Zabbix代理接收監控數據,後者用於從snmp trap文件讀取監控數據。當採用拉的工作模式時,由於每種監控項的具體拉取方式存在較大區別,因此poller類進程進一步劃分為多種進程,包括純poller進程、unreachable poller進程、ipmi manager與ipmi poller進程、icmp pinger進程、java poller進程、proxy poller進程和http poller進程。每一種poller進程負責拉取相應類型的監控數據。

預處理進程

預處理(preprocessing)進程是從Zabbix 3.4開始新增的一種進程類型,它用於對原始的監控數據進行各種形式的變換和計算,並通過共享記憶體,將輸出結果傳遞到history syncer進程進行處理。在Zabbix的早期版本中,預處理進程只能運行在Zabbix伺服器端,當數據量大時會給Zabbix伺服器端造成較大的壓力。因此從Zabbix 4.2版本開始,預處理進程可以同時運行在Zabbix伺服器端和Zabbix代理端。在這種情況下,由Zabbix代理負責採集的監控數據在傳輸到Zabbix伺服器端之前就已經完成了預處理,直接從Zabbix客戶端傳輸到Zabbix伺服器端的數據則需要由Zabbix伺服器端完成預處理。

[root@prod-zabbix-server ~]# ps -ef|grep preprocessing
zabbix    8652  8643  0 Feb21 ?        00:47:49 /usr/sbin/zabbix_server: preprocessing manager #1 [queued 0, processed 716 values, idle 5.029540 sec during 5.035809 sec]
zabbix    8653  8643  0 Feb21 ?        00:13:20 /usr/sbin/zabbix_server: preprocessing worker #1 started
zabbix    8654  8643  0 Feb21 ?        00:04:00 /usr/sbin/zabbix_server: preprocessing worker #2 started
zabbix    8655  8643  0 Feb21 ?        00:03:44 /usr/sbin/zabbix_server: preprocessing worker #3 started
zabbix    8656  8643  0 Feb21 ?        00:03:35 /usr/sbin/zabbix_server: preprocessing worker #4 started
zabbix    8657  8643  0 Feb21 ?        00:03:29 /usr/sbin/zabbix_server: preprocessing worker #5 started
zabbix    8658  8643  0 Feb21 ?        00:03:23 /usr/sbin/zabbix_server: preprocessing worker #6 started
zabbix    8659  8643  0 Feb21 ?        00:03:25 /usr/sbin/zabbix_server: preprocessing worker #7 started
zabbix    8660  8643  0 Feb21 ?        00:02:28 /usr/sbin/zabbix_server: preprocessing worker #8 started
zabbix    8661  8643  0 Feb21 ?        00:02:17 /usr/sbin/zabbix_server: preprocessing worker #9 started
zabbix    8662  8643  0 Feb21 ?        00:02:18 /usr/sbin/zabbix_server: preprocessing worker #10 started

以上命令結果可知,preprocessing進程由1個preprocessing manager(管理者進程)和多個preprocessing worker(工作者進程)進程組成。

processing manager進程負責監聽預處理所使用的Unix域套接字並處理由poller / trapper進程和preprocessing worker進程發送過來的消息。還會向lld manager進程發送消息,因為原始監控數據中同時包含LLD規則監控項數據,這些數據在預處理完畢以後還需要進行LLD處理(由lld manager和lld worker進程完成)

預處理工作者(preprocessing worker)進程的數量由配置參數StartPreprocessors決定,允許1~1 000個進程。工作者進程負責讀取管理者進程發送的進程間通訊服務消息,並執行所獲得的任務。

LLD進程

LLD進程是從Zabbix 5.0開始出現的專門負責LLD規則(LLD rule)監控數據處理的進程,由於底層發現(Low Level Discovery,LLD)得到越來越多的應用,因此這類數據的處理壓力隨之增加,將這些工作交給單獨的進程來處理將有利於性能的提升和將來的進一步擴展。

LLD進程包括lld manager進程和lld worker進程兩種,其中管理者進程是唯一的,工作者進程可以啟動多個。LLD進程只能運行在Zabbix伺服器端,它們位於預處理進程的下游,接收預處理進程發送的消息作為輸入,而輸出則是對各項監控配置的更新操作。本質上,LLD就是通過解析LLD規則監控項(一種特殊類型的監控項,其配置資訊存儲在items表中,其監控值不用於存儲,只用於更新監控配置)返回的特殊格式的字元串,創建、更新或者刪除監控項、觸發器、圖表或主機,使之與返回結果保持一致。由於LLD規則監控值會按照設定的頻率進行更新,因此Zabbix可以隨著數據的更新而動態調整監控對象、監控指標和監控參數等。從Zabbix 4.2開始,LLD規則的監控值跟普通監控項一樣可以進行預處理,在預處理結束以後,LLD進程再對數據進行解析並更新配置資訊,這一方式賦予用戶更多對LLD規則數據進行處理的能力,從而增強了底層發現的功能。

[root@prod-zabbix-server ~]# ps -ef|grep lld
zabbix    8663  8643  0 Feb21 ?        00:01:33 /usr/sbin/zabbix_server: lld manager #1 [processed 15 LLD rules, idle 5.385801sec during 5.385996 sec]
zabbix    8664  8643  0 Feb21 ?        00:29:15 /usr/sbin/zabbix_server: lld worker #1 [processed 14 LLD rules, idle 6.001249 sec during 6.150509 sec]
zabbix    8665  8643  0 Feb21 ?        00:29:28 /usr/sbin/zabbix_server: lld worker #2 [processed 15 LLD rules, idle 8.471019 sec during 8.725697 sec]

lld manager進程雖然只有一個,但是其需要完成的任務有多種,包括註冊lldworker進程、接收其他進程發送的消息、給lld worker進程分配任務、處理lldworker進程返回的結果以及響應隊列長度請求等。

lld worker進程負責處理lld manager進程分配的任務,即接收並處理通過進程間通訊服務發送過來的code 1100消息。總體的處理過程包括解析消息,驗證LLD規則有效性(通過ConfigCache),載入filter、LLD macros和overrides,解析LLD消息的JSON數組,進行配置資訊更新,以及根據LLD規則監控項狀態生成內部事件。lld worker進程的工作機制是被動模式,即發出註冊消息以後,並不會主動向管理者進程請求任務,而是等待管理者進程分配任務。

image-20220303143549989

預處理進程和LLD進程處於poller類進程和trapper類進程的下游,負責處理poller類進程和trapper類進程獲取的原始監控數據。預處理進程按照用戶設置的處理規則對數據進行變換和計算,處理之後的數據傳遞給history syncer進程處理。預處理進程通過進程間通訊服務方式與上游進程通訊。處理之後的數據寫入共享記憶體,供下游進程使用

history syncer進程

history syncer進程是Zabbix伺服器端最為核心的進程,它負責將監控數據(包括趨勢數據)寫入資料庫和寫入快取、生成並處理事件,以及處理動作(action)並生成升級序列(escalation)等。如果沒有history syncer進程,Zabbix伺服器將什麼也做不了:既不能處理監控數據,又不能生成事件,也不能進行告警。history syncer進程位於預處理進程的下游,它將預處理進程寫入HistoryCache和HistoryIndexCache的數據作為輸入。

history syncer進程的啟動數量由配置文件中的StartDBSyncers參數控制,允許1~100個進程。history syncer進程的作用是將HistoryCache和HistoryIndexCache中的監控值寫入資料庫中的history表和trends表,同時根據監控值計算觸發器表達式,決定是否觸發事件。該進程在Zabbix伺服器端和Zabbix代理端都存在,但是有所不同,這一點體現在程式碼清單9-1所示的進程標題中。在Zabbix伺服器端時,該進程既需要處理監控值(values),也需要處理觸發器(triggers),在Zabbix代理端時,該進程只需要處理監控值,而不需要處理觸發器,因為觸發器表達式統一由Zabbix伺服器端處理。本章講述Zabbix伺服器端的處理過程。

[root@prod-zabbix-server ~]# ps -ef|grep history
zabbix    8720  8643  0 Feb21 ?        00:30:13 /usr/sbin/zabbix_server: history syncer #1 [processed 10 values, 8 triggers in 0.004174 sec, idle 1 sec]
zabbix    8721  8643  0 Feb21 ?        00:30:28 /usr/sbin/zabbix_server: history syncer #2 [processed 12 values, 5 triggers in 0.004013 sec, idle 1 sec]
zabbix    8722  8643  0 Feb21 ?        00:30:38 /usr/sbin/zabbix_server: history syncer #3 [processed 24 values, 7 triggers in 0.006277 sec, idle 1 sec]
zabbix    8723  8643  0 Feb21 ?        00:30:21 /usr/sbin/zabbix_server: history syncer #4 [processed 4 values, 3 triggers in 0.004239 sec, idle 1 sec]
zabbix    8724  8643  0 Feb21 ?        00:30:30 /usr/sbin/zabbix_server: history syncer #5 [processed 236 values, 146 triggers in 0.058686 sec, idle 1 sec]
zabbix    8725  8643  0 Feb21 ?        00:30:18 /usr/sbin/zabbix_server: history syncer #6 [processed 0 values, 0 triggers in 0.000022 sec, idle 1 sec]

處理動作相關進程

escalator進程用於處理事件觸發的整個動作序列,該進程讀取escalations表中的數據並進行處理,並將生成的警報消息插入alerts表中,供alerter進程使用。所以,escalator進程並不實際發送警報消息,而只生成警報。

[root@prod-zabbix-server ~]# ps -ef|grep escalator
zabbix    8726  8643  0 Feb21 ?        00:00:32 /usr/sbin/zabbix_server: escalator #1 [processed 0 escalations in 0.001072 sec, idle 3 sec]

alerter進程族用於實際發送警報,該進程族包括alert syncer進程、alert manger進程和alerter進程。alert syncer進程負責將資料庫中的警報資訊和媒體類型資訊同步到alert manager進程,具體方法是從資料庫讀取數據,然後構造為進程間通訊服務消息並發送到alert manager進程。alert manager進程負責向alerter進程分發警報處理任務,並接收alerter進程回饋的結果。alerter進程負責按照alertmanager分配的任務處理警報並回饋結果。task manager進程運行在Zabbix伺服器端和Zabbix代理端,它負責處理存儲在資料庫task表中的遠程命令(remote command)、立即檢查(check now)、問題確認(problem acknowledge)和問題關閉(problem close)等任務。

[root@prod-zabbix-server ~]# ps -ef|grep alert
zabbix    8645  8643  0 Feb21 ?        00:00:44 /usr/sbin/zabbix_server: alert manager #1 [sent 0, failed 0 alerts, idle 5.006731 sec during 5.006787 sec]
zabbix    8646  8643  0 Feb21 ?        00:00:00 /usr/sbin/zabbix_server: alerter #1 [sent 0, failed 0 alerts, idle 657.095715 sec during 657.405902 sec]
zabbix    8647  8643  0 Feb21 ?        00:00:00 /usr/sbin/zabbix_server: alerter #2 [sent 0, failed 0 alerts, idle 656.705429 sec during 657.122473 sec]
zabbix    8648  8643  0 Feb21 ?        00:00:00 /usr/sbin/zabbix_server: alerter #3 [sent 0, failed 0 alerts, idle 656.675887 sec during 657.107786 sec]
zabbix    8649  8643  0 Feb21 ?        00:00:00 /usr/sbin/zabbix_server: alerter #4 [sent 0, failed 0 alerts, idle 656.699989 sec during 657.124047 sec]
zabbix    8650  8643  0 Feb21 ?        00:00:00 /usr/sbin/zabbix_server: alerter #5 [sent 0, failed 0 alerts, idle 656.677134 sec during 657.137743 sec]
zabbix    8651  8643  0 Feb21 ?        00:00:00 /usr/sbin/zabbix_server: alerter #6 [sent 0, failed 0 alerts, idle 658.772114 sec during 659.591568 sec]
zabbix    8746  8643  0 Feb21 ?        00:01:29 /usr/sbin/zabbix_server: alert syncer [queued 0 alerts(s), flushed 0 result(s) in 0.001063 sec, idle 1 sec]

優化建議

以4C8G配置、能夠處理監控項5萬個為例,相關進程優化項如下(僅供參考):

配置 默認值 推薦值
StartDBSyncers 4 8,不宜太高,默認值已能處理4000 NVPS
StartAlerters 3 6
StartDiscoverers 1 3
StartPollers 5 12
StartPreprocessors 3 6
StartProxyPollers 1 3
StartTrappers 5 12
StartLLDProcessors 2 3
StartEscalators 1 1