この記事はFOLIOアドベントカレンダー16日目の記事です。昨日の記事は @u_nationによるFlux+ViewModel(AAC)+Daggerで画面回転対応してみたでした。
Push v.s. Pull
モニタリングシステム、と一言で言っても死活監視やメトリクス監視といろいろあるものの、モニタリングシステムの議論の中で、そのモニタリングシステムが採用している方法が、 Push 型 アプローチなのか Pull 型 アプローチなのかについて議論になることがあります。
また、最近採用事例も増えている監視システムである Prometheus は Pull 型のアプローチがとられています。Push 型、Pull型、それぞれでどういう特徴があるのかについてもちょっと気になったので調べてみました。
Push 型アプローチとは
Push 型のアプローチでは、監視対象となるホストにエージェントをインストールし、各ホストのエージェントが監視サーバに対してデータを送信する形で実現がなされています。管理サーバ側で設定変更を行わずとも、新しい監視対象が増えた場合には、対象のサーバにエージェントを追加するだけで監視対象を増やすことができます。Push 型の監視システムとして以下のようなものがあります。
- StatsD
- Sensu
- Datadog
- Meckerel
Push 型の場合、開始対象のホストが、外部サーバからアクセスを受ける形ではないため、ファイアウォールなどで外部からのアクセスが制限されたネットワークの場合でも、簡単に導入が可能という面があります。Datadog や Mackerel といった SaaS 型の監視サービスでは、基本的に Push 型のアプローチをとられています。 (Pull 型の SaaS 監視サービスあったら知りたい)
敢えて挙げる欠点としては、監視対象を増やせば増やすほどサーバ側への負荷も高くなり、またサーバ側も監視対象のサーバが全部で何台あるのかを正確に把握できないため、増える負荷に対する対応がしづらいといったところがあるようにも思います。
利点
- 監視対象を増やす場合は エージェントをインストールするだけで簡易
- 監視対象が外からアクセスを受けるための設定が不要 (Pull 型と比べて)
欠点
- 監視対象が増えた時に監視サーバに負荷が集中しがち
Pull 型アプローチとは
Pull 型アプローチでは、監視サーバ上に監視対象についての設定を行い、監視対象からデータを集めてくる形のアプローチがとられています。 古くからある監視システムはこちらのアプローチをとっていることが多いように思います。Pull 型の監視システムとしては以下のようなものがあります。
- Nagios
- Zabbix
- Prometheus
Pull 型のものは監視対象を設定ファイルに書く必要があるため、監視対象が増えたりした場合には、その度に設定ファイルをアップデートする必要があります。また、Pull 型はサーバ側が監視対象にアクセスする必要が有ることから、ネットワーク的な設定が必要な場合があります。Zabbix proxy のような Proxy サーバを配置して、回避されることもあります。
また、監視サーバは監視対象をすべて把握しているため、監視対象からデータが取得できなかった場合には異常があると気づくことが容易にできます。Push型の場合、監視対象が対象から外れたのか、異常が発生して送信できなかったのかを区別することができません。
監視対象が増えて監視サーバ側の負荷が増えた場合にも、データスクレイプのタイミングをずらしたり長くすることで負荷軽減を行うなど柔軟な対応が取りやすいように思います。
欠点としては、Pull型の場合各監視対象の詳細なデータを取りたい場合、データ取得のためのエンドポイントやエージェントを用意しておく必要がある点でしょうか(Nagios の nrpe, Zabbix の zabbix agent, Prometheus の 各種 exporter)。
利点
- 監視対象一覧を知っているため、データを取得出来なかった時に異常に気づくことができる
- 監視サーバの負荷が高まった際に柔軟な対応がとりやすい
欠点
- データを expose するためのエージェントも各ホストで準備する必要がある
- AutoScaling 等で監視対象の数が変わった場合に、監視対象リストをアップデートする必要がある
Pull 型から Push 型へ
モニタリングシステムの変遷をみると、Nagios, Zabbix とサーバ側に設定ファイルをおき、監視対象をその設定ファイルに書いて監視を行う Pull 型のアプローチをとっているものが当初一般的でした(Zabbix は Active check を行うことも可能だけど)。ただ、IaaS 等のクラウドサービスが一般的になり、監視対象が動的にかわるようになるにつれ Pull 型のアプローチでは辛い部分がより目立つようになってきたように思います。 どのホストを監視対象とするのかをサーバ側で持つ Pull 型のアプローチでは、監視対象が動的に増えたりする環境では、設定ファイルをアップデートしていく仕組みを作成する必要があるからです。
そういった背景から、監視対象からメトリクスデータなどを送ってもらう Push 型のアプローチが注目を集めるようになったようなりました。監視ツール (フレームワーク?) である Sensu (https://sensuapp.org/) が出てきた時は、まさにその分散的なアプローチから、「クラウド時代の監視ツールだ!!」といろんな記事で紹介されていました。
"クラウド利用が一般的になった" ことで、監視対象が動的に変わるようになり、Pull 型のアプローチ から Push 型アプローチのほうに注目が移っていくようになりました。 ただそんな中登場した監視ツールである Prometheus (https://prometheus.io/) では Push 型ではなく Pull 型のアプローチがとられています。
Prometheus と サービスディスカバリ
Prometheus
- Prometheus (https://prometheus.io/)
Prometheus は SoundCloud 社によって開発され、OSS 化されたプロダクトです。CNCF (https://www.cncf.io/) のプロジェクトの一つともなっていて、現在採用事例も増えています。 もともと Google の SRE の人が Borgmon というGoogle の社内監視システムを元に作成されたそうです。
Prometheus では各監視したいホストにメトリクス取得用の exporter を入れ、Prometheus はその exporter の情報を取得・保管します。
例えば
$ docker run -d --name node-exporter -p 9100:9100 quay.io/prometheus/node-exporter
を実行すると、ホストの情報取得のための exporter を起動でき、 http://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 ...
のようなテキストが表示されます。メトリクスは簡単なテキストフォーマットで表されているだけなため、独自の Exporter も容易に作成できます。
上記 フォーマットについてはこちらが参考になります。 https://prometheus.io/docs/instrumenting/exposition_formats/
Pull + サービスディスカバリ
Pull 型アプローチの欠点として監視対象リストをアップデートする仕組みが必要であるという話をしました。 Prometheus ではサービスディスカバリとの連携を行うことでその欠点を補うようにしています。 その他の Pull 型の監視システムを使用した場合に、自分たちで作成が必要だった、監視対象の反映がビルトインされているという表現のほうが正しいかも知れません。
ちなみに Prometheus で用意されている サービスディスカバリの連携設定一覧は以下のようなものがあります。
- azure_sd_config (Azure)
- consul_sd_config (Consul)
- dns_sd_config (DNS)
- ec2_sd_config (AWS)
- openstack_sd_config (OpenStack)
- gce_sd_config (GCE )
- kubernetes_sd_config (Kubernetes)
- marathon_sd_config (Marathon)
- nerve_sd_config (Zookeeper)
- serverset_sd_config (Zookeeper)
- triton_sd_config (Triton)
- file_sd_config (Json ファイルからの読み込み)
AWSや GCPといったクラウドサービスでは、ホスト一覧を取得するためのAPIがあるため簡単にサービスディスカバリを使用することができます。 ただ、オンプレミスなどで利用するとなると、 Consul や Zookeeper 等のサービスを使う必要がありそうです。
Why pull rather than push?
Prometheus の FAQ にも Why do you pull rather than push? という項目があります。
Pulling over HTTP offers a number of advantages: - You can run your monitoring on your laptop when developing changes. - You can more easily tell if a target is down. - You can manually go to a target and inspect its health with a web browser. Overall, we believe that pulling is slightly better than pushing, but it should not be considered a major point when considering a monitoring system. For cases where you must push, we offer the Pushgateway.
と書かれており、Prometheus としても Push 型、Pull 型が大きな差別ポイントにはならないと考えているようです。
まとめ
Push 型、Pull 型の監視のアプローチと、Prometheus について調べた内容について少しまとめてみました。 今までは、 Prometheus が Pull 型のアプローチをとっているのは、Pull 型 → Push 型 → Pull 型 と昔の形に戻っただけかと考えていましたが、 Pull 型 → Push 型 → Pull + サービスディスカバリ連携 といった言い方のほうが正しいのかなと感じました。 今後は Push + ??? みたいなシステムもでてくるのかなと。
Prometheus は設定も容易で、各種ミドルウェアの exporter も豊富に用意されているのでオススメです。
FOLIO Advent Calendar 16日目の記事でした。明日は kenchan0130 によるFOLIO の iOS、Android、macOS の端末管理についての話です。
参考URL
Prometheus 関連の参考記事
- Prometheus について書いてみる
- Consul を Prometheus と連携させてみる