vSphere APIでVMのpower_stateを監視し、POWERED_OFF時にZabbixからEmail通知する
検証の概要
vSphere APIを使って特定のVMのpower_stateを定期的に取得し、VMがPOWERED_ONになった際にZabbixからEmail通知を送信します。
今回の構成では、ZabbixのScript ItemでvCenter APIを2段階で呼び出し、対象VMのpower_stateを取得します。その後、Zabbixのトリガー機能でpower_stateの値を評価し、トリガーアクションで事前に設定したユーザにメール通知を発報します。
利用するvSphere APIについて
APIでTokenを発行する
vSphere Automation APIのセッションエンドポイントに、Basic認証でアクセスします。以下は動作確認用の例です。パスワードはコマンドへ直接記述せず、環境変数や秘密情報管理機能から渡すことを推奨します。
bash
VCENTER_URL='https://vcenter01.demo.local'
VCENTER_USER='administrator@vsphere.local'
read -rsp 'vCenter password: ' VCENTER_PASSWORD
printf '\n'
ACCESS_TOKEN=$(curl -ks -X POST "${VCENTER_URL}/api/session" \
-H 'Content-Type: application/json' \
-u "${VCENTER_USER}:${VCENTER_PASSWORD}" \
| tr -d '"')/api/sessionのレスポンスは、JSON文字列としてTokenを返します。tr -d '"'は、レスポンスの前後にある引用符を取り除くために使用しています。
ラボ環境であるため、-kによるTLS証明書検証の無効化を利用しています
対象VMのpower_stateを取得する
今回は、VM名ではなくMOID形式のvm-55009を指定します。
VM情報はGET /api/vcenter/vm/{vm}で取得します。セッションTokenは、先のAPIで取得したTokenを、リクエストヘッダーのvmware-api-session-idに指定します。
bash
curl -ks -X GET \
'https://vcenter01.demo.local/api/vcenter/vm/vm-55009' \
-H "vmware-api-session-id: ${ACCESS_TOKEN}"power_stateには、主に次の値が返ります。
POWERED_ON: 電源オンPOWERED_OFF: 電源オフSUSPENDED: サスペンド
MOIDとは
MOID(Managed Object ID)は、vCenterが管理対象オブジェクトを識別するためのIDです。VMの場合、vm-55009のような値で表されます。
APIでVMを取得するときは、sample-vmのような表示名ではなく、APIが要求するVM識別子を指定します。VM名やIPなどの他の情報からMOIDを検索して活用する方法もありますが、今回は事前に取得したMOIDを直接利用しています。
なお、対象VMのMOIDはvSphere Clientで該当VMを選択している状態のURLに表示されます。
Zabbixの準備と設定手順
今回の設定手順は、次の流れです。
- Zabbix Applianceをインストールする
- Email通知を設定する
- 監視対象ホストを登録する
- Script itemを作成する
- Dependent itemを作成する
- トリガーを作成する
- トリガーアクションを作成する
- VMを起動・停止して動作をテストする
Zabbix Applianceのインストール
Applianceを利用する理由
Zabbix Applianceを利用すると、Zabbix Server、Webフロントエンド、データベースを含む監視環境を比較的短時間で構築できます。vSphere環境では、配布されているOVF形式のイメージを利用できます。Zabbix Applianceのダウンロード
ただし、Zabbix公式ドキュメントではApplianceは評価用途を想定しているため、本番環境では監視対象数、保存期間、データベース性能、バックアップ方式を考慮して構成を検討してください。Zabbix 7.0 Applianceマニュアル
インストール手順の概要
- ダウンロードページから、利用するバージョンのApplianceイメージを取得します。
- 任意の仮想環境にデプロイします。
- コンソールからデフォルトのパスワードでログイン可能です。
- デフォルトはDHCPです。必要に応じてStaticに変更します
- Zabbix Webインターフェースへログインします(デフォルトパスワード)
Email通知の設定
ZabbixのEmail通知では、次の3つを設定します。
- Emailメディアタイプ
- 通知先ユーザーのメディア
- トリガーアクション
Emailメディアタイプ
ZabbixのWebインターフェースで、Alerts > Media types > Emailを開き、SMTP環境に合わせて次の項目を設定します。
- SMTP server / SMTP server port
- Connection security
- Authentication
- SMTP helo / From
SMTPサーバーが認証を要求する場合は、専用の送信用アカウントを使用し、パスワードを設定ファイルや記事へ直接記載しないようにします。Zabbix公式ドキュメント: Email
通知先ユーザーのメディア
Usersから通知先ユーザーを開き、MediaタブでEmailを追加します。
- Type:
Email - Send to: 通知先メールアドレス
- When active: 通知を許可する時間帯
- Use if severity: 通知対象の深刻度
- Enabled: 有効
設定後、Emailメディアタイプのテスト機能でテストメールを送信します。テストメールが届くことを確認してから、トリガーアクションを設定します。メール通知の設定に関しては、Qiitaの参考記事を参考にさせていただきました。
監視対象ホストの登録
今回はVMへZabbix Agentをインストールしません。vCenter APIを監視するための論理ホストをZabbixへ登録します。
Data collection > Hostsを開きます。Create hostをクリックします。- Host nameに
vCenterなど、監視用途が分かる名前を入力します。 - Host groupsに
Hypervisorsなどのグループを指定します。 - Agent interfaceは、Agent監視を行わない場合は追加しません。
- ホストを保存します。
添付画像の最初の画面は、Data collection > HostsからCreate hostを選択し、vCenterホストを作成する例です。公開時は、画面内のユーザー名やパスワードなどの情報をマスキングしてください。
Script itemの作成
HTTP AgentではなくScript itemを使う理由
今回のREST APIは、一度Tokenを生成してから、そのTokenを使って本来のVM APIを呼び出す必要があります。
HTTP Agentでも単純なHTTPリクエストは実行できますが、今回のような「セッション取得」と「VM情報取得」の2段階処理を1つのアイテムで行うには、Script itemを使う方が実装しやすくなります。
ZabbixのScript itemはシェルスクリプトではなく、JavaScriptで記述します。HttpRequestオブジェクトでHTTPリクエストを送信し、レスポンスを返します。Zabbix公式ドキュメント: Script item
Script itemの設定
対象ホストのItemsでCreate itemをクリックし、次のように設定します。
| 項目 | 設定例 |
|---|---|
| Name | 任意 |
| Type | Script |
| Key | 任意 |
| Type of information | Text |
| Update interval | 1m |
curlコマンドをJavaScriptへ書き換える
以下は、Tokenを取得してからVM情報を取得するScript itemの例です。冒頭のAPIはCurlコマンドで例を示しました。vSphere ClientのAPI ExplorerでもサンプルはCurlで出してくれます。しかし、ZabbixのScript itemはJavascript形式で記述する必要がありますので、生成AI等で書き直してもらいましょう。/api/sessionのレスポンスはJSON文字列で返るため、外側の引用符を取り除いてからvmware-api-session-idヘッダーへ設定します。
※検証用の簡便さ重視で認証情報などをそのまま記載していますが、実際に実装する際の認証情報取り扱いにはご注意ください。
javascript
var p = JSON.parse(value);
var request = new HttpRequest();
var session;
var result;
// vCenter API のセッション取得
request.setHttpAuth(HTTPAUTH_BASIC, 'administrator@vsphere.local', '<Password>');
request.addHeader('Content-Type: application/json');
session = request.post(
'https://vcenter01.demo.local/api/session',
''
);
if (request.getStatus() != 201) {
throw 'Failed to get vCenter session. HTTP status: ' + request.getStatus();
}
// /api/session のレスポンスは JSON 文字列なので、引用符を除去
session = session.replace(/^"|"$/g, '');
// VM API 用にヘッダーを設定
request.clearHeader();
request.addHeader('vmware-api-session-id: ' + session);
// VM情報取得
result = request.get(
'https://vcenter01.demo.local/api/vcenter/vm/vm-55009'
);
if (request.getStatus() != 200) {
throw 'Failed to get VM information. HTTP status: ' + request.getStatus();
}
return result;Script itemのテスト
Script itemを保存したら、アイテムのTestまたは機能で記述に問題がないか(ちゃんと取得できるか)を確認できます。
※この時点ではAPIのレスポンス全体を保存します。power_stateだけを取り出す処理は、次に作成するDependent itemで行います。
Dependent itemの作成
Dependent itemを使う理由
Script itemで取得したJSONをそのまま保存し、Dependent itemで必要な値だけを抽出します。
この構成にすると、vCenter APIへのアクセスはMaster itemで1回だけ実行し、power_stateやVM名など複数の値を別々のDependent itemとして利用できます。対象項目が増えた場合にも、APIアクセスを増やさずに監視項目を追加できます。
作成手順
Data collection > Hosts > 対象ホスト > Itemsを開きます。- Script item(例:
vm55009-item)のメニューからCreate dependent itemを選択します。 - 次のように設定します。
| 項目 | 設定例 |
|---|---|
| Name | vm5509-power_state(任意) |
| Type | Dependent item |
| Key | vm5509.power_state(任意) |
| Type of information | Text |
| Master item | 親となるItemを選択 |
Preprocessingタブで処理を追加します。- 処理に
JSONPathを選択します。 - Parametersに
$.power_stateを入力します。 - 保存します。
トリガーの作成
Dependent itemのメニューからCreate triggerを選択するか、対象ホストのTriggersから作成します。
| 項目 | 設定例 |
|---|---|
| Name | vm5509-power_state_trigger(任意) |
| Severity | Highまたは環境に合わせた深刻度 |
| Expression | last(/vCenter/vm5509.power_state)="POWERED_OFF" |
Function に last()、Result に = POWERED_ON を設定しています。
ここで評価する値は、Master itemのJSONではなく、JSONPathでpower_stateを抽出したDependent itemです。VMが電源オフになると、直近値がPOWERED_ONになり、問題イベントが生成されます。
POWERED_ONにします。トリガーアクションの作成
トリガーが問題イベントを生成したときにEmailを送信するため、トリガーアクションを作成します。
Alerts > Actions > Trigger actionsを開きます。Create actionをクリックします。- Action nameに
vm5509-power_on_actionなど、用途が分かる名前を入力します。 - Conditionsに対象トリガーを指定します。
OperationsタブでSend messageを追加します。- 通知先ユーザーまたはユーザーグループを指定します。
Send to Media typeでEmailもしくはAll available指定します。- 必要に応じてRecovery operationにも復旧通知を追加します。
- 保存します。
以下の画像は、Alerts > Actions > Trigger actionsからアクションを作成し、対象トリガーへEmail送信オペレーションを追加する流れです。
電源オン検知のテスト
- 対象VMが
POWERED_OFFであることを確認。 - Script itemの値がJSONとして取得できることを確認。(Latest Data)
- Dependent itemの現在地値が
POWERED_OFFであることを確認。(Latest Data) - 対象VMを起動します。
- 次回の更新間隔後、Script itemがJSONを取得できていることを確認。
- Dependent itemが
POWERED_ONになったことを確認。 - トリガーが
PROBLEMになることを確認します。 - Emailが通知先へ届くことを確認します。
トラブルシューティング
Script itemがUnsupportedになる
- Zabbix Serverから
vcenter01.demo.localへ接続できるか確認する - TCP 443が通信可能か確認する
- vCenterのCA証明書を信頼できる状態か確認する
- ユーザー名、パスワード、権限を確認する
/api/sessionのHTTPステータスコードがScriptの判定値と一致しているか確認するvm-55009が対象VMの正しい識別子か確認する
Dependent itemの値が取得できない
- Master itemの最新値がJSONになっているか確認する
- JSONPathが
$.power_stateになっているか確認する - vCenterのレスポンスに
power_stateが含まれているか確認する - Type of informationが
Textになっているか確認する
Emailが届かない
- Emailメディアタイプのテストを実行する
- 通知先ユーザーのMediaが有効か確認する
- 通知時間帯と深刻度の条件を確認する
- アクションの条件が対象トリガーに一致しているか確認する
- Problems画面のActions欄で、Email送信が実行されたか確認する
まとめ
今回のポイントは、vCenter APIのレスポンス全体をScript itemで取得し、Dependent itemでpower_stateを抽出することです。
/api/sessionでvCenter APIのTokenを取得するvm-55009のようなVM識別子でVM情報を取得する- HTTP Agentではなく、2段階のAPI呼び出しが可能なScript itemを使う
- Script itemはシェルスクリプトではなくJavaScriptで記述する
- Dependent itemのJSONPathで
$.power_stateを抽出する POWERED_ONを条件にトリガーを発生させる- トリガーアクションでEmailを送信する
- 本番環境での接続時の認証情報や証明書検証オプションの扱いに注意
コメント
コメントを投稿