Ubuntu Weekly Recipe

第562回モニタリングツールPrometheusを使う

今回はモニタリングツールであるPrometheusを紹介します。

Prometheusとは

Prometheusは、もともとSoundCloudに依って開発されたモニタリングツールです。他のモニタリングツールにない特徴として、後述するクライアントであるExporterからメトリック(データ)を自分で取得しにいくpull型の構造を持っています[1]⁠。

Prometheus自体は大雑把に以下の3つの部分から構成されています。

  • メトリック取得対象(Exporter)を見つけ、取得する部分
  • 取得したメトリックを蓄える時系列データベース
  • 時系列データベースに蓄えたメトリックを検索するためのエンドポイント(HTTPサーバ)

Prometheus自体はgolangで書かれているため、ただ一つのバイナリを起動するのみで動作します。このためコンテナとの相性がよく、またパッケージの依存関係などを考慮する必要がないため既存の環境で試しに導入するハードルが比較的低いと言えます。

Prometheusのインストール

Ubuntuでは主に以下の方法でPrometheusがインストールできます。

aptレポジトリとsnapパッケージにあるPrometheusはいずれもバージョンが若干古いので、今回は手動で2019年3月時点で最新のver. 2.8.0のインストールを行います。前述のとおりにPrometheusそのものはバイナリ一つ起動すれば良いため、基本的にはバイナリと設定ファイル、daemon化のためのsystemd service unit fileの設置のみで作業が済みます[2]⁠。

まず、Prometheusを動作させるユーザとグループを作成します。

$ sudo groupadd prometheus
$ sudo useradd -d /var/lib/prometheus -g prometheus -s /bin/false -m prometheus

upstreamよりバイナリをダウンロードします。実際には以下が含まれます。

  • Promehteus本体のバイナリ
  • 設定ファイルのサンプル(prometheus.yml)
  • ユーティリティであるpromtoolのバイナリ
  • エンドポイントの画面を提供するconsole template(consoles)とそのライブラリ(console_libraries)
$ wget https://github.com/prometheus/prometheus/releases/download/v2.8.0/prometheus-2.8.0.linux-amd64.tar.gz
$ tar xf prometheus-2.8.0.linux-amd64.tar.gz
$ ls -1 prometheus-2.8.0.linux-amd64
console_libraries
consoles
LICENSE
NOTICE
prometheus
prometheus.yml
promtool

Prometheusとpromtoolのバイナリをパスが通った場所へ設置します。

$ sudo cp prometheus promtool /sbin/
$ sudo chown root:root /sbin/prometheus /sbin/promtool

設定ファイルディレクトリと時系列データベースのデータディレクトリを作成します。

$ sudo mkdir /etc/prometheus
$ sudo mkdir /var/lib/prometheus/data
$ sudo chown -R prometheus:prometheus /var/lib/prometheus/data

サンプルの設定ファイルと、console templateを設定ファイルディレクトリへ設置します。

$ sudo cp -r prometheus.yml consoles console_libraries /etc/prometheus/
$ sudo chown -R root:prometheus /etc/prometheus

最後に/etc/systemd/system/prometheus.serviceへsystemdのservice unit fileを設置します。

[Unit]
Description=Prometheus Server
Documentation=https://prometheus.io/docs/introduction/overview/
After=network-online.target

[Service]
User=prometheus
ExecStart=/sbin/prometheus --config.file=/etc/prometheus/prometheus.yml --storage.tsdb.path=/var/lib/prometheus/data --web.console.templates=/etc/prometheus/consoles  --web.console.libraries=/etc/prometheus/console_libraries
ExecStop=/bin/kill -TERM ${MAINPID}
ExecReload=/bin/kill -HUP ${MAINPID}

[Install]
WantedBy=multi-user.target

更新したunit fileを読み込み、Prometheusの起動とその確認を行います。

$ systemctl daemon-reload
$ systemctl start prometheus.service
$ systemctl status prometheus.service

ブラウザでPrometheusが起動しているホストの9090番ポートへアクセスしてみましょう。

すると図1のようなダッシュボードが表示されるはずです。ダッシュボードからは後述のPromQLをクエリしたり、メトリック取得対象のリストや状態を確認できます。

図1 PrometheusのHTTPエンドポイントのダッシュボード
画像

また、consoles/prometheus.htmlへアクセスすると、先程設置したconsole templateによって生成されたPromehtuesのStatusが確認できます。

図2 Prometheusのconsole template
画像

Node_Exporterのインストール

次にメトリック収集対象としてExporterをインストールします。

Exporterの実体はPrometheusから[3]HTTP GETを受けると関連するメトリックを収集し、Prometheusが解釈可能なテキストデータとして渡すというHTTPサーバです。

Exporterは公式・サードパーティのものを含めて様々なサービスや装置のメトリックを収集・提供するものが存在しています。また、Prometheusそのものも自分自身のメトリックを収集するExporterとして機能しています。今回は各ホストのCPUやメモリの使用量等のハードウェア関連のメトリックを収集するNode_Exporterをインストールします。

Node_Exporterもapt、snapパッケージDocker imageが用意されています。今回はこちらに関してもPrometheus同様に、2019年3月時点で最新のver. 0.17.0のpre-compiledバイナリ[4]を使用します。

先程Prometheusをインストールしたホストでupstreamよりバイナリをダウンロードし、Node_Exporterのバイナリを設置します。

$ wget https://github.com/prometheus/node_exporter/releases/download/v0.17.0/node_exporter-0.17.0.linux-amd64.tar.gz
$ tar xf node_exporter-0.17.0.linux-amd64.tar.gz
$ sudo cp node_exporter-0.17.0.linux-amd64/node_exporter /sbin/
$ sudo chown root:root /sbin/node_exporter

/etc/systemd/system/node_exporter.serviceへsystemdのservice unit fileを設置します。

[Unit]
Description=Node Exporter for Prometheus
After=network.target

[Service]
Type=simple
User=prometheus
ExecStart=/sbin/node_exporter
PrivateTmp=true

[Install]
WantedBy=multi-user.target

そして以下の手順でNode_Exporterを起動します。

$ systemctl daemon-reload
$ systemctl start node_exporter.service

起動できたらブラウザでNode_Exporterが起動しているホストの9100番ポートの/metricsへアクセスしてみましょう。すると図3のようなメトリックが画面に表示されます。

図3 Node_Exporterのメトリック
画像

また、curlなどを使用して直接HTTP GETでも確認できます。

$ curl localhost:9100/metrics
# HELP go_gc_duration_seconds A summary of the GC invocation durations.
# TYPE go_gc_duration_seconds summary
go_gc_duration_seconds{quantile="0"} 0
go_gc_duration_seconds{quantile="0.25"} 0
go_gc_duration_seconds{quantile="0.5"} 0
go_gc_duration_seconds{quantile="0.75"} 0
go_gc_duration_seconds{quantile="1"} 0
go_gc_duration_seconds_sum 0
go_gc_duration_seconds_count 0
# HELP go_goroutines Number of goroutines that currently exist.
# TYPE go_goroutines gauge
go_goroutines 6
# HELP go_info Information about the Go environment.
# TYPE go_info gauge
go_info{version="go1.11.2"} 1
(略)

Prometheusの設定ファイルとNode_Exporterの登録

PrometheusがExporterからメトリックを取得して、時系列データベースにデータを蓄えるためにはPrometheusにExporterを収集対象として登録する必要があります。

そのため、Prometheusの設定ファイルに先程起動したNode_Exporterの設定を追加します。

その前に、Prometheusのインストール時はサンプルのものをコピーするだけであった設定ファイルであるprometheus.ymlの中身を見ておきましょう。拡張子が示すとおりにYAML形式で設定が記載されています。

# my global config
global:
  scrape_interval:     15s # Set the scrape interval to every 15 seconds. Default is every 1 minute.
  evaluation_interval: 15s # Evaluate rules every 15 seconds. The default is every 1 minute.
  # scrape_timeout is set to the global default (10s).

# Alertmanager configuration
alerting:
  alertmanagers:
  - static_configs:
    - targets:
      # - alertmanager:9093

# Load rules once and periodically evaluate them according to the global 'evaluation_interval'.
rule_files:
  # - "first_rules.yml"
  # - "second_rules.yml"

# A scrape configuration containing exactly one endpoint to scrape:
# Here it's Prometheus itself.
scrape_configs:
  # The job name is added as a label `job=<job_name>` to any timeseries scraped from this config.
  - job_name: 'prometheus'

    # metrics_path defaults to '/metrics'
    # scheme defaults to 'http'.

    static_configs:
    - targets: ['localhost:9090']

Exporterからメトリックを取得する部分にのみ着目すると、以下の設定が施されています。

  • globalのscrape_intervalでExporterから15秒周期でメトリックを取得
  • scrape_configsに'prometheus'としてPrometheus自分自身のメトリックを取得するjobを定義

PrometheusでExporterからメトリックを取得する際にはExporter(サービス)毎などのまとまりでjobを作って、それぞれのjobに対して取得対象などを定義していきます。

それでは、設定ファイルにNode_Exporterの設定を追加していきましょう。/etc/prometheus/prometheus.ymlのscrape_configsの末尾に以下を追記します。

scrape_configs:

(略)

  - job_name: 'node'

    file_sd_configs:
    - files:
       - /etc/prometheus/nodes.yml

メトリック取得対象の定義にはサービスディスカバリ機能を用います。今回はfile_sd_configを使用します。file_sd_configでは別なYAMLファイルに収集対象のリストを書き下す形式です。

なお、サンプルに記載されていた'prometheus' jobではstatic_configが使用されていて、これはprometheus.ymlに収集対象を直書きする形式です。サービスディスカバリはstatic_configやfile_sd_config以外にも KubernetesAmazon EC2Microsoft Azure と連携したサービスディスカバリや、DNSのSRVレコードを使用したもの など複数存在しています。

file_sd_configに定義した/etc/prometheus/nodes.ymlへ先程起動したNode_Exporterを登録します。基本的にはtargetsに<対象ホスト>:9100と並べ立てていくのみです。また、labelsを使用することで、メトリックに任意のラベルを付加できます。今回はroleという名前のラベルを定義し、値にprometheusを入れています。ラベルは後述のPromQLでキーとして使用できるため、複数台のホストがある時「このロールのマシンだけでデータを集計したい」ということがあるケースで効力を発揮します。

- targets:
   - localhost:9100
  labels:
    role: prometheus

設定を追加したら、promtoolのシンタックスチェック機能を使用して設定ファイルをチェックしましょう。

$ promtool check config /etc/prometheus/prometheus.yml 
Checking /etc/prometheus/prometheus.yml
  SUCCESS: 0 rule files found

問題がなければPrometheusをreloadして、ブラウザでPrometheusのダッシュボードの/targetsにアクセスしてみましょう。画面に'node'という項目とlocalhost:9100が存在しているようであればNode_Exporterの登録に成功しています図4⁠。

図4 Node_Exporter登録後のPrometuehsのダッシュボードのtarget画面
画像

PromQLを使用したグラフの描画

Prometheusでは時系列データベースに対してPromQL という独自のクエリ言語を使用してグラフの描画やデータの加工、アラートの生成などの全般的なデータ操作を行います。このためPrometheusを使用する上でPromQLの使用は必須となります。

PromQLの簡単な例をいくつか紹介します。

PromQLの発行クライアントとして、Prometheusのダッシュボードが使えますのでブラウザでアクセスします。

一番上のテキストボックスに以下を入力してエンターキーを押下すると、先程追加したNode_Exporterで取得したload1というロードアベレージの一分間の平均値を取得したメトリックの時系列グラフを取得できます図5⁠。

node_load1{instance="localhost:9100"}
図5 load1のグラフ
画像

また、テキストボックスに以下を入力してエンターキーを押下すると、Node_Exporterから収集した各コア、各モード(idle以外)のCPU使用率の時系列グラフを取得できます図6注5⁠。

irate(node_cpu_seconds_total{instance="localhost:9100", mode!="idle"}[1m]) * 100
図6 CPU使用率のグラフ
画像

上記のクエリでは、node_cpu_seconds_totalという各コア、各モードのCPU使用時間の累計を記録したメトリックのlocalhostで、かつ直近1分間のデータのうちmodeがidle以外なものを指定しています注6注7⁠。そして、irate()という一秒あたりの率を計算する関数へ渡し、結果をパーセントの形にするために100倍しています。

Grafanaのインストールとダッシュボードの作成

先に紹介したPrometheusのダッシュボードはグラフを可視化するものですが、これはあくまで一時的なものであり、画面を閉じると消えてしまいます。また、複数のメトリックを一つのグラフに描画するということも(少なくとも容易には)できません[8]⁠。

Prometheusの可視化ツールとしてのデファクトスタンダードはGrafanaです。PrometheusのダッシュボードとGrafanaでは基本的には以下の使い分けをします。

  • 何か確認したいことや、異常があった時の調査では、PrometheusダッシュボードからPromQLをクエリして確認する
  • 日常的によく見るものに関してはGrafanaダッシュボードにグラフを作成しておく

Grafanaは公式のインストールドキュメントに従ってインストールし、Grafanaを起動します。

$ sudo /bin/bash -c "echo deb https://packages.grafana.com/oss/deb stable main > /etc/apt/sources.list.d/grafana.list"
$ curl https://packages.grafana.com/gpg.key | sudo apt-key add -
$ sudo apt update
$ sudo apt install grafana
$ sudo systemctl start grafana-server.service 

Grafanaの起動後、ブラウザでGrafanaをインストールしたホストの3000番ポートへアクセスすると、ログイン画面が表示されるのでadminユーザでログインします。デフォルトパスワードはadminで、入力後即座に本パスワードの設定を促されます。

ログイン後データソースとしてPrometheusを追加します。⁠Add Data Source」をクリックし、Prometheusを選択します図7図8⁠。

図7 初回ログイン時のダッシュボード
画像
図8 データソースの追加画面。絞り込みでPrometheusのみが表示されるようにしている
画像

Prometheusの設定画面に入りますので、⁠URL」へPrometheusのURLを入力し、⁠Save & Test」をクリックします図9⁠。テストが成功すればPrometheusの登録は完了です。

図9 Prometheusの設定画面。URLにPrometheusのURLを入力すれば良い
画像

データソースを追加すれば後はダッシュボードにPromQLを入力して任意のグラフなどを表示できます図10⁠。

図10 Node_Exporterの一部のメトリックをグラフ表示するダッシュボード。いずれもPromQLを実行した結果を出力している
画像

また、GrafanaはGrafana Labにアップロードされているダッシュボードをダウンロードして使用することもできます。

おすすめ記事

記事・ニュース一覧