Prometheus 使用 PushGateway 進行數據上報採集

1、PushGateway 介紹

Prometheus 是一套開源的系統監控、報警、時間序列數據庫的組合,最初有 SoundCloud 開發的,後來隨着越來越多公司使用,於是便獨立成開源項目。Prometheus 基本原理是通過 Http 協議週期性抓取被監控組件的狀態,而輸出這些被監控的組件的 Http 接口爲 Exporter。PushGateway 作爲 Prometheus 生態中的一個重要一員,它允許任何客戶端向其 Push 符合規範的自定義監控指標,在結合 Prometheus 統一收集監控。

PushGateway 使用場景:

  • Prometheus 採用定時 Pull 模式,可能由於子網絡或者防火牆的原因,不能直接拉取各個 Target 的指標數據,此時可以採用各個 Target 往 PushGateway 上 Push 數據,然後 Prometheus 去 PushGateway 上定時 pull。
  • 其次在監控各個業務數據時,需要將各個不同的業務數據進行統一彙總,此時也可以採用 PushGateway 來統一收集,然後 Prometheus 來統一拉取。

2、環境、軟件準備

本次演示環境,我是在虛擬機上安裝 Linux 系統來執行操作,以下是安裝的軟件及版本:

  • Oracle VirtualBox: 5.1.20 r114628 (Qt5.6.2)
  • System: CentOS Linux release 7.3.1611 (Core)
  • Docker: 18.06.1-ce
  • Prometheus: v2.11.1
  • PushGateway: 1.0.0

注意:這裏爲了快速方便啓動 Prometheus、PushGateway 服務,我使用 Docker 方式啓動,所以本機需要安裝好 Docker 環境,這裏忽略 Docker 的安裝過程。其中 Prometheus 安裝配置,可以參照之前文章 Prometheus 監控報警系統 AlertManager 之郵件告警,這裏着重介紹一下如何啓動並配置 PushGateway 並配置數據上報到 Prometheus。

3、PushGateway 安裝配置

PushGateway 安裝很簡單,可以使用二進制包解壓安裝服務,也可以使用 Docker 啓動服務。

3.1、二進制包安裝

二進制包安裝方式,直接從 官方 Github 下載最新二進制安裝包,解壓即可。

$ wget https://github.com/prometheus/pushgateway/releases/download/v1.0.0/pushgateway-1.0.0.linux-amd64.tar.gz
$ tar xzvf pushgateway-1.0.0.linux-amd64.tar.gz 
$ mv pushgateway-1.0.0.linux-amd64 /usr/local/pushgateway

使用命令 ./pushgateway 命令即可啓動服務,此時瀏覽器訪問 http://<ip>:9091 即可訪問 UI 頁面,只不過默認 Metrics 上沒有任何數據展示,那是因爲我們還沒有往 PushGateway 上推送任何數據。
prometheus-pushgateway
不過,PushGateway 服務本身是帶了一些 Metrics 的,可以通過訪問 http://<ip>:9091/metrics 地址來獲取,可以看到裏邊包含了 go、process 等相關的一些監控指標。
prometheus-pushgateway-metrics

3.2、Docker 安裝

使用 Docker 方式安裝啓動就更簡單了,直接獲取最新版官方鏡像 prom/pushgateway:latest 啓動命令如下:

$ docker run -d -p 9091:9091 prom/PushGateway 

啓動完畢後,同上方法驗證是否啓動成功。這裏爲了方便演示,我採用 Docker 方式啓動 PushGateway。

OK,現在 PushGateway 服務已經啓動完畢,但是還沒有跟 Prometheus 關聯起來,我們需要的是通過 PushGateway 來上傳自定義監控數據,然後通過 Prometheus 採集這些數據來進行監控。那麼就需要將 PushGateway 添加到 Prometheus 目標任務中去,增加 prometheus.yml 配置如下:

...
- job_name: 'pushgateway'
    static_configs:
      - targets: ['172.30.12.167:9091']
        labels:
          instance: pushgateway

說明一下,這裏採用 static_configs 靜態配置方式,因爲目前就一個 PushGateway,如果有多個可以考慮其他服務發現方式,來方便動態加載,具體可以參考 這裏。配置完畢後,重啓 Prometheus 服務,此時可以通過 Prometheus UI 頁面的 Targets 下查看是否配置成功。
prometheus-pushgateway

4、API 方式 Push 數據到 PushGateway

接下來,我們要 Push 數據到 PushGateway 中,可以通過其提供的 API 標準接口來添加,默認 URL 地址爲:http://<ip>:9091/metrics/job/<JOBNAME>{/<LABEL_NAME>/<LABEL_VALUE>},其中 <JOBNAME> 是必填項,爲 job 標籤值,後邊可以跟任意數量的標籤對,一般我們會添加一個 instance/<INSTANCE_NAME> 實例名稱標籤,來方便區分各個指標。

接下來,可以 Push 一個簡單的指標數據到 PushGateway 中測試一下。

$ echo "test_metric 123456" | curl --data-binary @- http://172.30.12.167:9091/metrics/job/test_job

執行完畢,刷新一下 PushGateway UI 頁面,此時就能看到剛添加的 test_metric 指標數據了。
prometheus-pushgateway
不過我們會發現,除了 test_metric 外,同時還新增了 push_time_secondspush_failure_time_seconds 兩個指標,這兩個是 PushGateway 系統自動生成的相關指標。此時,我們在 Prometheus UI 頁面上 Graph 頁面可以查詢的到該指標了。
prometheus-pushgateway

這裏要着重提一下的是,上圖中 test_metric 我們查詢出來的結果爲 test_metric{exported_job="test_job",instance="pushgateway",job="pushgateway"} ,眼尖的會發現這裏頭好像不太對勁,剛剛提交的指標所屬 job 名稱爲 test_job ,爲啥顯示的爲 exported_job="test_job" ,而 job 顯示爲 job="pushgateway" ,這顯然不太正確,那這是因爲啥?其實是因爲 Prometheus 配置中的一個參數 honor_labels (默認爲 false)決定的,我們不妨再 Push 一個數據,來演示下添加 honor_labels: true 參數前後的變化。

這次,我們 Push 一個複雜一些的,一次寫入多個指標,而且每個指標添加 TYPEHELP 說明。

$ cat <<EOF | curl --data-binary @- http://172.30.12.167:9091/metrics/job/test_job/instance/test_instance
# TYPE test_metrics counter
test_metrics{label="app1",name="demo"} 100.00
# TYPE another_test_metrics gauge
# HELP another_test_metrics Just an example.
another_test_metrics 123.45
EOF

添加完畢,再刷新一下 PushGateway UI 頁面,可以看到添加的數據了。
prometheus-pushgateway
從上圖可以看出,/metrics/job/test_jobmetrics/job/test_job/instance/test_instance 雖然它們都屬於 test_job,但是它們屬於兩個指標值,因爲 instance 對二者做了區分。此時我們訪問 Prometheus UI 頁面上 Graph 頁面查詢該指標。
prometheus-pushgateway
依舊有問題,那麼修改一下 prometheus.yaml,增加 honor_labels: true 參數配置如下:

...
- job_name: 'pushgateway'
    honor_labels: true
    static_configs:
      - targets: ['172.30.12.167:9091']
        labels:
          instance: pushgateway

重啓 Prometheus,稍等一會,等到 Prometheus 採集到數據後,我們再訪問 Prometheus UI 頁面上 Graph 頁面查詢該指標。
prometheus-pushgateway
此時,可以看到能夠正確匹配到 Push 的指標值對應到 job 和 instance 上了。這裏說明一下 honor_labels 的作用:因爲 Prometheus 配置 PushGateway 的時候,也會指定 job 和 instance,但是它只表示 PushGateway 實例本身,不能真正表達收集數據的含義。所以配置 PushGateway 需要添加 honor_labels:true 參數,避免收集數據本身的 job 和 instance 被覆蓋。詳細可參考 這裏 官網文檔對該參數的說明。

上邊我們 Push 指標數據是通過命令行追加方式,少量數據還湊合,如果需要 Push 的數據比較大時,就不太方便了,這裏我們也可以通過將指標數據寫入到文件,然後將文件內容提交,也可以正常添加到 PushGateway。新建一個指標數據文件 pgdata.txt 如下:

$ vim pgdata.txt
# TYPE http_request_total counter
# HELP http_request_total get interface request count with different code.
http_request_total{code="200",interface="/v1/save"} 276
http_request_total{code="404",interface="/v1/delete"} 0
http_request_total{code="500",interface="/v1/save"} 1
# TYPE http_request_time gauge
# HELP http_request_time get core interface http request time.
http_request_time{code="200",interface="/v1/core"} 0.122

然後執行如下命令,將數據 Push 上去。

curl -XPOST --data-binary @pgdata.txt http://172.30.12.167:9091/metrics/job/app/instance/app-172.30.0.0

執行完畢,在 PushGateway UI 頁面同樣能夠查詢的到。
prometheus-pushgateway
最後,如果要刪除某一個指標,同樣可以通過 API 方式觸發刪除。例如刪除 job="test_job" 組下的所有指標值,可以執行如下命令:

$ curl -X DELETE http://172.30.12.167:9091/metrics/job/test_job

注意:刪除 job="test_job" 組下的所有指標值,不包括 {job="test_job", instance="test_instance"} 中的指標值,雖然它們的 job 名稱都爲 test_job。如果想刪除該指標值,那麼需要執行如下命令:

curl -X DELETE http://172.30.12.167:9091/metrics/job/test_job/instance/test_instance

同樣,我們也可以在 PushGateway UI 頁面指定指標記錄後邊,點擊 Delete Group 按鈕來刪除,這裏就不在演示了。

5、用 Client SDK Push 數據到 Pushgateway 示例

通過 Client SDK 推送 metric 信息到 PushGateway,官方示例中支持 python、java、go 等不同語言類型 client,這裏我以 java 語言爲例,來演示下如何 Push 數據到 Pushgateway 中。

首先,pom.xml 中添加 simpleclient_pushgateway 依賴包。

<dependency>
    <groupId>io.prometheus</groupId>
    <artifactId>simpleclient_pushgateway</artifactId>
    <version>0.7.0</version>
</dependency>

編寫一個簡單 demo 如下:

public static void main(String[] args) {
    try{
        String url = "172.30.12.167:9091";
        CollectorRegistry registry = new CollectorRegistry();
        Gauge guage = Gauge.build("my_custom_metric", "This is my custom metric.").create();
        guage.set(23.12);
        guage.register(registry);
        PushGateway pg = new PushGateway(url);
        Map<String, String> groupingKey = new HashMap<String, String>();
        groupingKey.put("instance", "my_instance");
        pg.pushAdd(registry, "my_job", groupingKey);
    } catch (Exception e){
        e.printStackTrace();
    }
}

執行完畢後,訪問一下 Pushgateway UI 頁面,能夠查詢的到該指標。
prometheus-pushgateway
上邊列子比較簡單,咱們在來一個稍微負載一些的,指定多個 label 標籤組的指標。

public static void main(String[] args) {
    try{
        String url = "172.30.12.167:9091";
        CollectorRegistry registry = new CollectorRegistry();
        Gauge guage = Gauge.build("my_custom_metric", "This is my custom metric.").labelNames("app", "date").create();
        String date = new SimpleDateFormat("yyyy-mm-dd HH:mm:ss").format(new Date());
        guage.labels("my-pushgateway-test-0", date).set(25);
        guage.labels("my-pushgateway-test-1", date).dec();
        guage.labels("my-pushgateway-test-2", date).dec(2);
        guage.labels("my-pushgateway-test-3", date).inc();
        guage.labels("my-pushgateway-test-4", date).inc(5);
        guage.register(registry);
        PushGateway pg = new PushGateway(url);
        Map<String, String> groupingKey = new HashMap<String, String>();
        groupingKey.put("instance", "my_instance");
        pg.pushAdd(registry, "my_job", groupingKey);
    } catch (Exception e){
        e.printStackTrace();
    }
}

同樣,在 Pushgateway UI 頁面,也能夠查詢的到該指標。
prometheus-pushgateway

6、使用 PushGateway 注意事項

  • 指標值只能是數字類型,非數字類型報錯。

    $ echo "test_metric 12.34.56ff" | curl --data-binary @- http://172.30.12.167:9091/metrics/job/test_job_1
    text format parsing error in line 1: expected float as value, got "12.34.56ff"
    
  • 指標值支持最大長度爲 16 位,超過16 位後默認置爲 0

    $ echo "test_metric 1234567898765432123456789" | curl --data-binary @- http://172.30.12.167:9091/metrics/job/test_job_2
    # 實際獲取值
    test_metric{job="test_job_2"}	1234567898765432200000000
    
  • PushGateway 數據持久化操作

    默認 PushGateway 不做數據持久化操作,當 PushGateway 重啓或者異常掛掉,導致數據的丟失,我們可以通過啓動時添加 -persistence.file-persistence.interval 參數來持久化數據。-persistence.file 表示本地持久化的文件,將 Push 的指標數據持久化保存到指定文件,-persistence.interval 表示本地持久化的指標數據保留時間,若設置爲 5m,則表示 5 分鐘後將刪除存儲的指標數據。

    $ docker run -d -p 9091:9091 prom/pushgateway "-persistence.file=pg_file –persistence.interval=5m"
    
  • PushGateway 推送及 Prometheus 拉取時間設置

    Prometheus 每次從 PushGateway 拉取的數據,並不是拉取週期內用戶推送上來的所有數據,而是最後一次 Push 到 PushGateway 上的數據,所以推薦設置推送時間小於或等於 Prometheus 拉取的時間,這樣保證每次拉取的數據是最新 Push 上來的。

參考資料

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