iT邦幫忙

2023 iThome 鐵人賽

DAY 11
1

StatsD Logo

資訊處理流程 生成 收集 儲存 使用
StatsD Library
StatsD
StatsD Exporter

StatsD 於 2011 年由 Etsy 開源,它是一個使用 Node.js 撰寫的 Daemon,主要用途是接收應用程式或其他 Exporter 發送的指標資料,如計數、計時等資訊。收集到的指標可儲存於多種 Data Backend,與 Graphite 的搭配最為常見。但其實 Esty 的 StatsD 是重新優化實作後的版本,它的設計靈感來自於 Flickr 在 2008 年開發的 Perl 版 StatsD

Pipeline

Etsy 於 2005 年創立,目前為 S&P 500 成分股之一,股價為 $64.72。它是以手工藝品為主的線上拍賣平台,台灣的 Pinkoi 便是借鑑了 Etsy 的商業模式。Etsy 在 2010 年就實現了持續部署(Continues Deployment),將網站部署從原先需四人協同、耗費一小時的流程,縮短至只需一人、兩分鐘即可完成。然而,快速大量的部署不應犧牲品質,因此 Etsy 重新開發了 StatsD 來收集指標資料。透過即時的 Metrics,他們能迅速確定是否有服務異常,若有問題也能立即定位或回滾到先前的版本。此外,特別推薦一篇由 Etsy 的前首席工程師 Dan McKinley 的技術簡報 「選擇無聊的技術」,分享他們在 Etsy 時如何做技術選型,在這個工具多如繁星的時代,他的心得應該也很具有啟發性。

Concepts

Metrics Type

StatsD 的指標格式如下:

<metricname>:<value>|<type>

主要有三種 Metrics Type:

  1. Counter 計數:數值從 0 開始,可增加任何正整數,但不可減少。可用於記錄 Request 總數或錯誤次數。當 StatsD 將資料傳送至 Backend 時,該資料會在 StatsD 內重置為 0。例如:request_total:1|c
  2. Timer 計時:用於測量特定操作的所需時間(ms),並計算統計數據如平均值、最大值、最小值和百分位數。可用於記錄 Request 處理時間或 SQL 執行時間。例如:request_duration:100|ms
  3. Gauge 量測:代表一個可以任意增減的數值。可用於記錄記憶體使用狀況或當前活躍使用者數量。例如:可指定值 active_users:100|g、增加值active_users:+20|g、減少值active_users:-10|g

UDP

當利用 StatsD 收集指標時,預設會使用 UDP。Etsy 在初次介紹 StatsD 的文章中提到,選擇 UDP 的原因是它速度快且訊息送後不理,這意味著當應用程式傳送數據後不需等待確認,因此不會對效能有太多影響。但由於 UDP 不保證數據傳輸的完整性,可能導致指標數據不完整或錯誤。但如果 StatsD 因某些原因無法運行,這也確保應用程式不會因此而出現其他問題,且指標偏向輔助使用,遺失部分指標內容對應用程式穩定性較無影響。

StatsD Library

由於 StatsD 主要負責接收指標,所以指標的生成和傳送需要由應用程式自行處理。以下是一些常用的指標生成 Library 供參考:

  1. Python:pystatsddatadog
  2. Node.js:hot-shots
  3. Java:java-dogstatsd-client

DataDog

DataDog 是一家提供監控服務的 SaaS 公司。使用者可以透過他們的 SDK,將各種監控數據傳送至 DataDog。他們使用的指標格式基於 StatsD,並同樣使用 UDP 進行傳輸。但 DataDog 有根據自身需求,重新設計了一版 DogStatsD 的 StatsD,其中加入了 Histogram、Distribution 等不同的指標類型,並增加了 Tagging 功能。這些調整使得 DataDog 在收集和分析指標時更為方便,且在使用上更趨近於 Prometheus。

StatsD Exporter

若你對使用 UDP 進行指標傳輸以提高效能感興趣,但仍希望使用 Prometheus 儲存和查詢指標,可以參考 Prometheus 團隊開發的 StatsD Exporter。這個工具可以透過 UDP 接收 StatsD 格式的指標,再將其轉換成 Prometheus 格式供其爬取。如需更多 Prometheus 的 Label 功能,可以搭配使用由 DataDog 重新設計的 DogStatsD 的 Library DataDog,Lab 中有實作範例可供參考。

StatsD Exporter Pipeline

D for Daemon

在多數工具的命名中,我們經常看到以 D 結尾的名稱,如本文的 StatsD 或是收集 Log 的 Fluentd。這個 D 就是指 Daemon,代表該程式為背景執行的服務。Daemon 通常用於接收資料或背景執行特定工作。

在 Daemon 的 Wiki 裡面有寫到,Daemon 是 Demon(惡魔)較早的拼寫形式。BSD文件中介紹 Daemon 時提到在「Unit 系統管理手冊」中對 Daemon 有以下的說明:

許多人將「daemon」與「demon」這兩個詞等同,藉此暗示 UNIX 與陰間的某種邪惡有所關聯。這是一種極壞的誤解。「Daemon」事實上是「demon」另一種早得多的寫法;daemon 並無善或惡的傾向,相反,它定義一個人的品質或性格。古希臘的「個人 Daemon」概念類似於現代的「守護神」概念——快樂是得到友好靈魂幫助或保護的狀態。一般來說,UNIX系統看起來的確是充斥著守護神和惡鬼。

Lab

範例程式碼:11-statsd

Quick Start

StatsD + Graphite

  1. 啟動所有服務

    docker-compose up -d
    
  2. 檢視服務

    1. FlaskAPI: http://localhost:8000

      1. 透過瀏覽器發送 Request

        1. http://localhost:8000
        2. http://localhost:8000/io_task
        3. http://localhost:8000/cpu_task
        4. http://localhost:8000/random_sleep
        5. http://localhost:8000/random_status
      2. 或是使用 k6 發送 Request

        k6 run --vus 1 --duration 300s k6-script.js
        
    2. Graphite Web UI: http://localhost

      1. 確認指標收集結果,展開左側選單 Metrics > stats > timers > flask > request_durations_seconds > count,若未出現 flask 選單,請等待一段時間後重新整理頁面
      2. 或是直接進入 http://localhost/render?from=-10mins&until=now&target=stats.timers.flask.request_duration_seconds.count
    3. Grafana: http://localhost:3000,登入帳號密碼為 admin/admin

      1. 進入 Explore 選單,Data Source 選擇 Graph,Series 依序選擇 statstimersflaskrequest_duration_secondscount,再執行 Query 即可看到指標資料
  3. 關閉所有服務

    docker-compose down
    

StatsD Exporter + Prometheus

  1. 啟動所有服務

    docker-compose -f docker-compose.exporter.yaml up -d
    
  2. 檢視服務

    1. FlaskAPI: http://localhost:8000

      1. 透過瀏覽器發送 Request

        1. http://localhost:8000
        2. http://localhost:8000/io_task
        3. http://localhost:8000/cpu_task
        4. http://localhost:8000/random_sleep
        5. http://localhost:8000/random_status
      2. 或是使用 k6 發送 Request

        k6 run --vus 1 --duration 300s k6-script.js
        
    2. StatsD Exporter: http://localhost:9102/metrics

      1. 檢視 StatsD Exporter 收集轉換成 Prometheus Metrics 的 Metrics
    3. Prometheus: http://localhost:9090

      1. 檢視是否有 flask 開頭的 Metrics
    4. Grafana: http://localhost:3000,登入帳號密碼為 admin/admin

      1. 點擊左上 Menu > Dashboards > Flask Monitoring,即可看到透過 Provisioning 建立的 Dashboard
  3. 關閉所有服務

    docker-compose -f docker-compose.exporter.yaml down
    

Goals

透過 StatsD 收集 Flask API 的 Metrics

  1. StatsD + Graphite: 使用 docker-compose.yml
    1. 使用 All in One Image: graphiteapp/docker-graphite-statsd 將 StatsD 與 Graphite 一起啟動
    2. 使用 Graphite web UI 確認指標收集結果
    3. Flask API 透過標準的 StatsD Library statsd 產生 Metrics
  2. StatsD Exporter + Prometheus: 使用 docker-compose.exporter.yml
    1. 使用 StatsD Exporter 將 StatsD 資料轉換成 Prometheus Metrics
    2. 使用 Prometheus 收集 Metrics
    3. 使用 Grafana 查詢 Prometheus Metrics
    4. Flask API 透過 DataDog 重新實作的 DogStatsD 的 Library DataDog 產生 Metrics

小結

儘管近年來較少聽到有人討論 StatsD,但在某些特定情境下,例如:對應用程式效能要求較高、應用程式無法設定 Endpoint 供 Prometheus 抓取指標,或是一些資深的工具預設提供 StatsD 指標輸出時(例如 Gunicorn預設監控功能),可以想起還有 StatsD 這個老朋友。

儘管 StatsD 沒有被列在 CNCF 的 Observability Tool 中但還是特別在本系列中介紹,是因為使用 StatsD Exporter 搭配 Prometheus 是我第一次接觸監控時學到的搭配組合,也算是滿有感情的,所以也有再把當時學到的東西整理於 Flask Monitoring 以及 Gunicorn Monitoring,若對於 StatsD 有興趣也可以參考看看。

參考資料

  1. Measure Anything, Measure Everything
  2. Tracking Every Release
  3. Quantum of Deployment
  4. Introduction to StatsD
  5. docker-graphite-statsd
  6. Monitoring StatsD: metric types, format + code examples

上一篇
Thanos - 統御 Prometheus 群集的霸者
下一篇
Zabbix - 指標界的沙場老兵
系列文
時光之鏡:透視過去、現在與未來的 Observability30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言