prometheus常用表達式

Prometheus強大的地方就在於可以使用很多計算公式去獲取自己需要的數據。正因爲涉及到了計算公式,這也是它的難點所在,比如在Zabbix中要獲取CPU使用率是一件很簡單的事情,而在Prometheus中卻需要使用計算公式來完成。

比如要統計CPU使用率:node_exporter會抓取CPU常用的8種狀態的累計工作時間,然後再用(所有非空閒狀態的CPU時間總和)/(所有狀態的CPU時間總和)= CPU使用率。而如果想要獲取中間某一分鐘的CPU平均時間還需要用到Counter數據類型。由於Counter的數據一直是增量,所以需要截取其中一段增量值,然後再拿這個數值去套用公式進行計算。


Prometheus爲不同的數據類型提供了非常多的計算函數,有個小技巧就是遇到counter數據類型,在做任何操作之前,先套上一個rate()或者increase()函數。下面介紹一些比較常用的函數幫助理解:

rate()函數:這是一個非常重要的函數,專門配合counter類型數據,取counter在這個時間段中的平均每秒增量。比如監控網絡接受字節數的情況,在9:10到9:20期間累計量增加了1000bytes,加入rate([1m])函數後就會使用1000除以60秒,計算出數據大約爲16bytes。

1rate(  node_network_receive_bytes[1m] )  #獲取1分鐘內每秒的增量


increase函數和rate()函數一樣也是配合Counter使用。區別就是它是取其中一段時間的增量而不是平均值,比如

1increase(node_cpu[1m])  #獲取CPU總使用時間1分鐘的增量


sum函數:在實際工作中CPU大多是多核的,而node_cpu會將每個核的數據都單獨顯示出來,我們其實不會關注每個核的單獨情況,而是關心總的CPU情況。使用sum()函數進行求和後可以得出一條總的數據,但sum()是將所有機器的數據都進行了求和,所以還要再使用by (instance)或者by (cluster_name)就可以取出單個服務器或者一組服務器的CPU數據。上面的公式可以進化爲:

1sum( increase(node_cpu[1m]) )


count函數該函數用於進行一些模糊判斷,比如有100臺服務器在監控,想實現當CPU使用率大於80%的機器達到N臺就進行報警就可以使用它

1count(count_netstat_wait_connections > 200)


topk函數:該函數可以從大量數據中取出排行前N的數值,N可以自定義。比如監控了100臺服務器的320個CPU,用這個函數就可以查看當前負載較高的那幾個,用於報警

1topk(3,count_netstat_wait_connections)  #Gauge類型


2topk(3,,rate(node_network_receive_bytes[20m]))  #Counter類型


delta()函數

delta(v range-vector)計算範圍向量v中每個時間系列元素的第一個和最後一個值之間的差值,返回具有給定增量和等效標籤的即時向量。 delta被外推以覆蓋範圍向量選擇器中指定的全時間範圍,因此即使樣本值都是整數,也可以獲得非整數結果。

以下示例表達式返回現在和2小時之前CPU溫度的差異:

delta(cpu_temp_celsius{host="zeus"}[2h])

delta應僅用於儀表。


changes()函數

changes(v range-vector) 輸入一個區間向量, 返回這個區間向量內每個樣本數據值變化的次數(瞬時向量)。例如

# 如果樣本數據值沒有發生變化,則返回結果爲 1changes(node_load5{instance="192.168.1.75:9100"}[1m]) # 結果爲 1



predict_linear函數:對曲線變化速率進行計算,起到一定的預測作用。比如當前這1個小時的磁盤可用率急劇下降,這種情況可能導致磁盤很快被寫滿,這時可以使用該函數,用當前1小時的數據去預測未來幾個小時的狀態,實現提前告警

1predict_linear( node_filesystem_free_bytes{mountpoint="/"}[1h],4*3600 ) < 0   #如果未來4小時後磁盤使用率爲負數就會報警



瞭解清楚流程之後進行一個CPU使用率的拆分解析:

1、先把key找出來,比如是爲了查看CPU的使用率,那麼就應該使用node_cpu這個key

2、在node_cpu這個key的基礎上把idle的CPU時間和全部CPU時間過濾出來,使用{}做過濾,如下:

1node_cpu{ mode='idle' }  #找出空閒CPU的值
2node_cpu  #不寫其他參數代表ALL


3、使用increase()函數把1分鐘的數據抓取出來,這個時候取出來的是每個CPU的數據

1increase(node_cpu{mode='idle'}[1m])


4、使用sum()函數求和每個CPU的數據,得到單獨一個數據

1sum( increase(node_cpu{mode='idle'}[1m]) )


5、sum()函數雖然把每個CPU的數據進行了求和,但是還把每臺服務器也進行了求和,所有服務器的CPU數據都相同了,還需要進行一次處理。這裏又引出了一個新函數 by (instance)。它會把sum求和到一起的數值按照指定方式進行拆分,instance代表的是機器名。如果不寫by (instance)的話就需要在{}中寫明需要哪個實例的數據。

1sum( increase(node_cpu{mode='idle'}[1m]) ) by (instance)  #空閒CPU一分鐘增量


6、最終計算出CPU使用率

11-( sum( increase(node_cpu{mode='idle'}[1m]) ) by (instance) / sum(increase(node_cpu[1m])) by (instance) ) *100



附上三個常用的計算公式:

查看源碼打印?

1#CPU使用率
2100 - (avg(irate(node_cpu_seconds_total{mode="idle"}[5m])) by (instance) * 100)
3#內存使用率
4(node_memory_MemFree_bytes+node_memory_Cached_bytes+node_memory_Buffers_bytes) / node_memory_MemTotal_bytes * 100
5#空閒內存剩餘率
6100 - (node_memory_MemFree_bytes+node_memory_Cached_bytes+node_memory_Buffers_bytes) / node_memory_MemTotal_bytes * 100
7#磁盤使用率
8100 - (node_filesystem_free_bytes{mountpoint="/",fstype=~"ext4|xfs"} / node_filesystem_size_bytes{mountpoint="/",fstype=~"ext4|xfs"} * 100)


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章