PrometheusをVPSで動かしてAlertmanagerでメール通知するまで

# はじめに

* Prometheusの特に__Alertmanager__を試したくて今回構築しました


* VPSやメール配信サービスも含めて申込からはじめるというほぼゼロスタートです
    * 申込方法や外部サービスの設定は割愛します


# 環境

## Prometheusなどのバージョン
* prometheus-1.7.1.linux-amd64
* node_exporter-0.14.0.linux-amd64
* alertmanager-0.7.1.linux-amd64

## サーバ
* [DTI ServersMan＠VPS](http://dream.jp/vps/)
    * CentOS 7 (64bit)
    * HDD:50GB
    * メモリ:1GB

### 理由：
* 安くてrootが使えるため。

## メール送信
* [SendGrid](https://sendgrid.kke.co.jp/)
    * プラン：シンプル
    * SMTP

### 理由：
* 無料でけっこうな数のメールが送れるため。
* 審査はしっかりしているので[お名前.com](https://www.onamae.com/)でドメインを取りました。
* より開発者に使いやすい[mailgun](https://www.mailgun.com/)というサービスもあるようです。

## SSHクライアント
* [vSSH](https://itunes.apple.com/jp/app/vssh/id527244258?mt=8)

### 理由：
* iOSで使えるため。
* 最初はLite(無料)でしたがセッションが2個までだったので途中で有料にしました。

## 作業クライアント
* iPhone7
* Bluetoothキーボード
* ディスプレイとコネクタ
    * AirPlay
    * Apple純正コネクタ

### 理由：
* 特に理由はありません。
* ノートPCなど使いやすい環境で大丈夫だと思います。

# 手順
## Prometheus
### ダウンロードする

* 適当なディレクトリに移動します
    * 置きポンで動くのがいいところです
* 圧縮ファイルをダウンロードします
    * 他のバージョンは[こちら](https://prometheus.io/download/)
    
``` console:
$ wget https://github.com/prometheus/prometheus/releases/download/v1.7.1/prometheus-1.7.1.linux-amd64.tar.gz
```

* 直接ダウンロードできない環境ではインターネットにつながる環境でダウンロードしたファイルをサーバ上に配置します


### 解凍する

* ダウンロードしたファイルを解凍します

``` console:
$ tar xvfz prometheus-1.7.1.linux-amd64.tar.gz
```

* ディレクトリが出来ます

``` console:
$ ls
prometheus-1.7.1.linux-amd64
prometheus-1.7.1.linux-amd64.tar.gz
```

### 設定する
* 出来たディレクトリに移動します

``` console:
$ cd prometheus-1.7.1.linux-amd64
```

* 元々ある設定ファイルをバックアップします（念のため）

``` console:
$ cp prometheus.yml prometheus.yml.bkyyyymmdd
$ ls
prometheus.yml
prometheus.yml.bkyyyymmdd
```
※ほかのディレクトリやファイルもありますが省略しています

* 元々書いてある内容をすべて消して下記を書きます。

``` yml:prometheus.yml
global:
  scrape_interval:    5s

scrape_configs:
  - job_name: 'prometheus'
    static_configs:
    - targets: ['localhost:9090']
```

### とりあえず起動する
* 実行します
* INFOログが数行出てきます
    * 最後にリッスンしているポート番号が出てきます

``` console:
$ ./prometheus -config.file=prometheus.yml
INFO[0000] Starting prometheus (version=1.7.1, branch=master, revision=3afb3fffa3a29c3de865e1172fb740442e9d0133   source="main.go:88"
・・・
INFO[0001] Listening on :9090   source="web.go:259"
```

### 確認する

* 先ほどのポートにアクセスします
* 次のような画面が開きます

※インターネットからアクセスできる場合は、localhostの部分をGlocal IPまたはドメイン名に読み替えてください

``` url:
http://localhost:9090/graph
```

![Prometheus Time Series Collection and Processing Server.png](https://qiita-image-store.s3.amazonaws.com/0/171468/22430ee2-9c91-037f-edb5-c3d984833725.png)

* prometheus本体が収集(?)しているメトリクスは次のURLで確認できます

``` url:
http://localhost:9090/metrics
```

![localhost9090metrics.png](https://qiita-image-store.s3.amazonaws.com/0/171468/57f4ff80-ad51-a94b-2f70-99dca4eb1738.png)

* prometheusやexporterのUPや、メモリ使用率は次のURLで確認できます
    * [まだ開発途中](https://www.youtube.com/watch?v=WUkNnY65htQ)のようですが十分使えます。

``` url:
http://localhost:9090/consoles/prometheus.html
```

![localhost9090consolesnode_prometheus.png](https://qiita-image-store.s3.amazonaws.com/0/171468/df48effc-73da-998e-57a8-be3506724e3d.png)


### 停止する
* 起動したセッションで、``` Ctrl + c ``` を押します
* stoppedのようなINFOログがでます

``` console:
・・・
INFO[1129] Local storage stopped.   source="storage.go:484"
$ 
```


## node_exporter

### ダウンロードする

* 適当なディレクトリに移動します
    * exporterも置きポンです
* 圧縮ファイルをダウンロードします
    
``` console:
$ wget https://github.com/prometheus/node_exporter/releases/download/v0.14.0/node_exporter-0.14.0.linux-amd64.tar.gz
```

### 解凍する

* ダウンロードしたファイルを解凍します

``` console:
$ tar xvfz node_exporter-0.14.0.linux-amd64.tar.gz
```

* ディレクトリが出来ます

``` console:
$ ls
node_exporter-0.14.0.linux-amd64
node_exporter-0.14.0.linux-amd64.tar.gz
```

### 設定する

* prometheusディレクトリに移動します

``` console:
$ cd ../prometheus-1.7.1.linux-amd64
```

* 下記をprometheus.ymlのscrape_configs：に追記します

``` yml:
  - job_name: 'node'
    static_configs:
    - targets: ['localhost:9100']
```

* prometheus.ymlはこうなります

``` yml:prometheus.yml
global:
  scrape_interval:    5s

scrape_configs:
  - job_name: 'prometheus'
    static_configs:
    - targets: ['localhost:9090']

  - job_name: 'node'
    static_configs:
    - targets: ['localhost:9100']
```


### とりあえず起動する
* 実行します
* INFOログが数十行出てきます
    * 最後にリッスンしているポート番号が出てきます

``` console:
$ ./node_exporter
INFO[0000] Starting node_exporter (version=0.14.1, branch=master, revision=840ba5dcc71a084a3bc64cb606003c1f94435a6   source="node_exporter.go:140"
・・・
INFO[0000] Listening on :9100   source="node_exporter.go:186
```

### 確認する

* 先ほどのポートにアクセスします
* 次のような画面が開きます

``` url:
http://localhost:9100/metrics
```

![localhost9100metrics.png](https://qiita-image-store.s3.amazonaws.com/0/171468/a84441b0-26df-1a75-1683-bb9f7ade6c22.png)

※ prometheusとの違いは、"node_"から始まるメトリクスがあることのようです


* prometheusのconsole画面の左側にnodeとあるのでクリックします
* node_exporterがUPしてるのが分かります

``` url:
http://localhost:9090/consoles/prometheus.html
```

![localhost9090consolesnode.png](https://qiita-image-store.s3.amazonaws.com/0/171468/8d304630-661d-1a2d-8576-15e4e16bdf44.png)


### 停止する
* 起動したセッションで、``` Ctrl + c ``` を押します

※　私の環境ではstoppedのような停止が分かるログは特に出ずにコンソール画面に戻りました。

``` console:
^C
$ 
```

## Alertmanager
### ダウンロードする

* 適当なディレクトリに移動します
    * これもほぼ置きポンです
* 圧縮ファイルをダウンロードします
    
``` console:
$ wget https://github.com/prometheus/alertmanager/releases/download/v0.7.1/alertmanager-0.7.1.linux-amd64.tar.gz
```

* 直接ダウンロードできない環境ではインターネットにつながる環境でダウンロードしたファイルをサーバ上に配置します


### 解凍する

* ダウンロードしたファイルを解凍します

``` console:
$ tar xvfz alertmanager-0.7.1.linux-amd64.tar.gz
```

* ディレクトリが出来ます

``` console:
$ ls
alertmanager-0.7.1.linux-amd64
alertmanager-0.7.1.linux-amd64.tar.gz
```

### 設定する（Alertmanagerの.ymlファイル）

「xx秒の間に来たアラートは同じとみなす」や「1回通知したら次の通知はxx時間後」などはここで設定します。
（個人的にAlertmanagerの一番良い機能だと思っています）
使うメールサーバのアドレスやfromやtoなどもここで設定します。


* 出来たディレクトリに移動します

``` console:
$ cd alertmanager-0.7.1.linux-amd64
```

* 元々ある設定ファイルをバックアップします（念のため）

``` console:
$ cp simple.yml simple.yml.bkyyyymmdd
$ ls
simple.yml
simple.yml.bkyyyymmdd
```

* 次の内容で修正していきます
    * 全て消してこれだけ書いても大丈夫だとは思いますが、まだ私はやっていません
    * SendGridを利用しています

``` yaml:simple.yml
global:
  smtp_smarthost: 'smtp.sendgrid.net:587'
  smtp_from: 'aaaaaaa@jibunnodomain.net'
  smtp_auth_name: 'apikey'
  smtp_auth_password: 'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx'

templates:
- '/etc/alertmanager/template/*.tmpl'

route:
  group_by: ['alertname', 'cluster', 'service']
  group_wait: 30s
  group_interval: 15m
  repeat_interval: 10m

  receiver: team-Z-mails

inhibit_rules:
- source_match:
    severity: 'critical'
  target_match:
    severity: 'warning'
  equal: ['alertname', 'cluster', 'service']

receivers:
- name: 'team-X-mails'
  email_configs:
  - to: 'xxxxxxx@jibundomain.net'

- name: 'team-Y-mails'
  email_configs:
  - to: 'yyyyyyy@jibundomain.net'

- name: 'team-Z-mails'
  email_configs:
  - to: 'zzzzzzz@taninnodomain.ne.jp'
```

#### はまったポイント（[SendGrid](https://sendgrid.kke.co.jp/blog/?p=3659)）
* smtp_authの、'apikey'は __固定文字列（アルファベットで apikey ）__ です。
* smtp_auth_passwordは、APIキーを作成したときに自動で設定されるとても長い英字の文字列です
* smtp_fromの、＠以降は取得したドメインにしましょう。＠以前はなんでもいいようです。


### 設定する（prometheusの.rulesファイル）

アラートを発報するルールはここで設定します。

* prometheusディレクトリに移動します

``` console:
$ cd ../prometheus-1.7.1.linux-amd64
```

* 空の.rulesファイルをつくります。

``` console:
$ touch alerts.rules
$ ls
alerts.rules
```

* 次の内容で修正していきます

``` :alerts.rules
ALERT InstanceDown
  IF up == 0
  FOR 5m
  LABELS { severity = "critical" }
  ANNOTATIONS {
    summary = "Instance {{ $labels.instance }} down",
    description = "{{ $labels.instance }} of job {{ $labels.job }}"
  }
```

### 設定する（ルールファイル名を指定する） 

* prometheusディレクトリに移動します

``` console:
$ cd ../prometheus-1.7.1.linux-amd64
```

* 下記をprometheus.ymlに追記します

``` yml:
rule_files:
  - 'alerts.rules'
```

* prometheus.ymlはこうなります

``` yml:prometheus.yml
global:
  scrape_interval:    5s

rule_files:
  - 'alerts.rules'

scrape_configs:
  - job_name: 'prometheus'
    static_configs:
    - targets: ['localhost:9090']

  - job_name: 'node'
    static_configs:
    - targets: ['localhost:9100']
```



### とりあえず起動する
* 実行します
* INFOログが数行出てきます
    * 最後にリッスンしているポート番号が出てきます

``` console:
$ ./alertmanager -config.file=simple.yml -mesh.peer-id=00:00:00:00:00:00
INFO[0000] Starting alertmanager (version=0.7.1, branch=master, revision=ab4138299b94c8dc554ea96e2ab28d04b048059   source="main.go:109"
・・・
INFO[0000] Listening on :9093   source="main.go:308"
```

#### はまったポイント（Alertmanagerが起動しない）

* とりあえず実行したら下記のようなエラーが出て起動できない

``` console:
$ ./alertmanager -config.file=simple.yml

panic: no valid network interfaces

gorouting 1 [running]:
main.mustHardwareAddr(0xc7f3e0,  0xc4200fal60)
        /go/src/github.com/prometheus/alertmanager/cmd/alertmanager/main.go:477 +0x14f
main.main()
        /go/src/github.com/prometheus/alertmanager/cmd/alertmanager/main.go:97 +0x2748

$
```

* [こちらのページ](https://github.com/prometheus/alertmanager/issues/582)を読んで、仮想サーバはMACAddressを敢えて設定しない事があるからAlertmanagerがMACAddressを一意値として利用しているが取得できていないと解釈（合ってるかはわかりません）
* ``` -mesh.hardware-addr``` オプションを付ければよさそうだが、付けてもそのようなオプションはないと
* もう少し調べると ``` -mesh.hardware-addr``` ではなく ``` -mesh.peer-id``` との[githubページ](https://github.com/prometheus/alertmanager/pull/638) を見つける
* オプションの引数（String）を何を設定していいかわからないので、とりあえずMACAddressっぽい文字列「00:00:00:00:00:00」を入れる
* 起動成功！


### 確認する

* 先ほどのポートにアクセスします
* 次のような画面が開きます

``` url:
http://localhost:9093/#/status
```

![localhost9093status_alertmanager.png](https://qiita-image-store.s3.amazonaws.com/0/171468/dedcb217-5880-55c1-137d-42ecdea12588.png)



### 停止する
* 起動したセッションで、``` Ctrl + c ``` を押します
* exiting grecefullyとmaintenance doneのようなINFOログがでます

``` console:
・・・
INFO[0173] received SIGTERM, exiting gracefully...   source="main.go:335"
・・・
INFO[0173] maintenance done   component=nflog duration=238.638μs source="nflog.go:286"
$ 
```



## メール通知できるか確認する

* node_exporter　→　prometheus　→　alertmanagerの順で起動します
    * prometheusの起動オプションに``` -alertmanager.url=http://localhost:9093 ``` を追加します

``` console:node_exporter
$ ./node_exporter
```

``` console:prometheus
$ ./prometheus -config.file=prometheus.yml -alertmanager.url=http://localhost:9093
```

``` console:alertmanager
$ ./alertmanager -config.file=simple.yml -mesh.peer-id=00:00:00:00:00:00
```



* prometheusのメニューから次を確認していきます

* Status＞Targetsを確認します

``` url:
http://localhost:9090/targets
```

![localhost9090status_up.png](https://qiita-image-store.s3.amazonaws.com/0/171468/0834d28e-a2c4-513d-81b2-5f7ea9dc2709.png)
※ UPしてます

* Status＞Rulesを確認します

![localhost9090rule_up.png](https://qiita-image-store.s3.amazonaws.com/0/171468/81dd0fbd-9ed3-e1c5-4465-e4a3cc3a48ba.png)
※ 設定したruleが書かれています

* Alertsを確認します

![localhost9090alerts_up.png](https://qiita-image-store.s3.amazonaws.com/0/171468/428a07ed-180e-ed7a-0197-348fe5afa0f9.png)
※ 緑色で InstanceDown は 0 active です


* node_exporterだけ停止します

![localhost9090status_down.png](https://qiita-image-store.s3.amazonaws.com/0/171468/810e78dc-50d5-b0d7-4919-854571710657.png)
※ DOWNしました！

* 再度、Alertsを確認します

![localhost9090alerts_pending.png](https://qiita-image-store.s3.amazonaws.com/0/171468/22e44409-6e92-0a8a-fd9e-05c35970e6f8.png)
※ Statusは __PENDING__ です
※ DOWNしたことは検知していますが、通知はgroup_intervalで設定したとおり5分待っている状態です。えらい！

* 5分後にAlertsを確認します

![localhost9090alerts_firing.png](https://qiita-image-store.s3.amazonaws.com/0/171468/94f0ed67-0446-f6ed-89a7-795adbdb7a16.png)
※ Statusが __FIRING__ に変わりました！

* 通知メールの受信を確認します

![alertmanager_firingmail.png](https://qiita-image-store.s3.amazonaws.com/0/171468/282a9702-a8f1-b370-42f6-bcba7af4e87c.png)
※　メールを受信しました！！！

* しばらくして再度通知メールの受信を確認します

![alertmanager_firingmail_2.png](https://qiita-image-store.s3.amazonaws.com/0/171468/ad715323-5df7-760d-9536-b32206464da1.png)
※　2通目のメールを受信しました！！！
※　repeat_intervalに設定したとおり、10分後（group_interval＝5分を加えて15分後？）に受信しました！！！


# おわりに
* ほぼ置きポンでここまでいきつけるのがとても好印象です
* Prometheus周りで大きくハマることも少なかったです
* 特にAlertmanagerがよく考えられてて、システム運用を長年やってきた者としてもっと使っていきたいと思いました
* テキストログの監視ができるようになればな、と思いました
    * [動画]((https://www.youtube.com/watch?v=uV_sh7_lVw8&list=PLqm7NmbgjUExeDZU8xb2nxz-ysnjuC2Mz&index=1))で「metrics, not logs.」と説明されてたので、自分で対応するしかないと思ってます。情報あればほしいところです。

* 正直、私はあまりこういう構築系はやってきませんでした
    * Linuxコマンド（wgetやvimの使い方）をGoogleで調べながら進めています
    * __そんな自分でも３～４日くらいでできました！__


# 参考情報
* [Prometheus.io - Getting  Started](https://prometheus.io/docs/introduction/getting_started/)
* [Monitoring a Machine with Prometheus: A Brief Introduction](https://www.youtube.com/watch?v=WUkNnY65htQ)
* [Keynote: Prometheus: From Berlin to Bonanza - Brian Brazil, CEO, Robust Perception](https://www.youtube.com/watch?v=uV_sh7_lVw8&list=PLqm7NmbgjUExeDZU8xb2nxz-ysnjuC2Mz&index=1)
* [次世代監視の大本命！ Prometheus を実運用してみた](http://qiita.com/sugitak/items/ff8f5ad845283c5915d2)
* [長生村本郷Engineers'Blog - Alertmanager 構築手順](http://kenzo0107.hatenablog.com/entry/2017/02/02/101011)
* [1.0が出てたのでPrometheusに入門してみた](http://qiita.com/kiida/items/d1fefccbe3e72293c251)

ほんとうに参考になりました。感謝いたします。


# 以上