ライブ マイグレーションの通知を取得する


メタデータ サーバーは、scheduling/ メタデータ ディレクトリ リストと maintenance-event メタデータキーを使用して、仮想マシン(VM)インスタンスのスケジューリング オプションと設定に関する情報を提供します。これらのメタデータ キーを使用すると、VM のスケジューリング オプションの詳細を確認できます。また、メンテナンス イベントの発生を通知することもできます。

デフォルトでは、すべての VM(Z3(プレビュー)を除く)にライブ マイグレーションが設定されています。メタデータ サーバーは、VM インスタンスのライブ マイグレーションが開始される前にメンテナンス イベントの通知を受け取ります。ただし、別のスケジューリング オプションを選択している場合は、メンテナンス イベントと VM の動作が異なることがあります。メンテナンス イベントとイベント中の VM の動作の詳細については、ホスト メンテナンスの概要をご覧ください。

始める前に

  • Windows Server VM の場合は、PowerShell 3.0 以降を使用します。コピーしたコードブロックを貼り付ける場合は ctrl+v の使用をおすすめします。
  • まだ設定していない場合は、認証を設定します。認証とは、Google Cloud サービスと API にアクセスするために ID を確認するプロセスです。ローカル開発環境からコードまたはサンプルを実行するには、次のように Compute Engine に対する認証を行います。

    このページの Python サンプルをローカル開発環境から使用するには、gcloud CLI をインストールして初期化し、自身のユーザー認証情報を使用してアプリケーションのデフォルト認証情報を設定してください。

    1. Google Cloud CLI をインストールします。
    2. gcloud CLI を初期化するには:

      gcloud init
    3. Google アカウントのローカル認証情報を作成します。

      gcloud auth application-default login

    詳細については、 ローカル開発環境の認証の設定 をご覧ください。

ライブ マイグレーションの通知を取得する

メンテナンス イベントの発生時に通知を受けるようにするには、maintenance-event メタデータキーに対するクエリを定期的に実行します。

メンテナンス イベントの発生で maintenance-event メタデータキーが更新されるのは、VM のスケジューリング オプションを migrate に設定している場合か、VM に GPU が接続されている場合に限ります。

このメタデータキーの値は、メンテナンス イベントが開始する 60 秒前に変更されます。アプリケーションのコード内に、メンテナンス イベントの発生前に実行したいタスク(データのバックアップ、ログの更新など)をトリガーする方法を記述します。

つまり、次の場合にのみ Compute Engine は 60 秒前の警告を表示します。

  • メンテナンス イベントの発生時にライブ マイグレーションを実行するように VM の可用性オプションが設定されている。

  • 前回のメンテナンス イベントの後に maintenance-event メタデータキーに対するクエリを 1 回以上実行している。

    • maintenance-event メタデータキーに対してクエリが実行されていない場合、または前回の移行後にメタデータキーにクエリが実行されていない場合、Compute Engine は VM でメンテナンス イベントの事前警告が必要ないと判断します。メンテナンス イベントはすぐに開始し、60 秒前の警告はスキップされます。

    • 60 秒警告がスキップされないようにするには、クライアント コードで移行イベントの合間に少なくとも 1 回 maintenance-event メタデータキーに対するクエリが実行されるようにしてください。このメタデータキーが監視されていることを Compute Engine が判断するために、maintenance-event メタデータキーに対して直接クエリを実行する必要があります。それより上位にあるメタデータのクエリでは、事前通知はトリガーされません。

GPU を接続している VM の場合は、VM が停止する 60 分前に値が変わるため、シャットダウンして別のホストで再起動する時間的余裕があります。GPU が接続している VM はライブ マイグレーションの対象外のため、インスタンスが停止します(指定があれば再起動します)。詳細については、GPU ホスト メンテナンス イベントの処理をご覧ください。

特定の VM セットの場合、VM のメンテナンスにより柔軟なオプションを使用できます。詳細については、ホスト メンテナンス イベントのモニタリングと計画をご覧ください。

メンテナンス イベントのメタデータキーをクエリする

Linux VM

Linux VM で maintenance-event メタデータキーにクエリを実行するには、次のコマンドを実行します。

user@myinst:~$ curl http://metadata.google.internal/computeMetadata/v1/instance/maintenance-event -H "Metadata-Flavor: Google"

出力は次のようになります。

NONE

Windows VM

Windows VM で maintenance-event メタデータキーにクエリを実行するには、次のコマンドを実行します。

PS C:\> 
$value = (Invoke-RestMethod `
         -Headers @{'Metadata-Flavor' = 'Google'} `
         -Uri "http://metadata.google.internal/computeMetadata/v1/instance/maintenance-event")
$value

出力は次のようになります。

NONE

Python

maintenance-event メタデータキーを更新待機機能とともに使用すると、メンテナンス イベントの開始時と終了時にスクリプトやアプリケーションに通知できます。これにより、イベントの前後に実行するアクションを自動化できます。

次の Python サンプルは、この 2 つの機能を組み合わせて実装する方法を示しています。


import time
from typing import Callable, NoReturn, Optional

import requests


METADATA_URL = "http://metadata.google.internal/computeMetadata/v1/"
METADATA_HEADERS = {"Metadata-Flavor": "Google"}


def wait_for_maintenance(callback: Callable[[Optional[str]], None]) -> NoReturn:
    """
    Start an infinite loop waiting for maintenance signal.

    Args:
        callback: Function to be called when a maintenance is scheduled.

    Returns:
        Never returns, unless there's an error.
    """
    url = METADATA_URL + "instance/maintenance-event"
    last_maintenance_event = None
    last_etag = "0"

    while True:
        r = requests.get(
            url,
            params={"last_etag": last_etag, "wait_for_change": True},
            headers=METADATA_HEADERS,
        )

        # During maintenance the service can return a 503, so these should
        # be retried.
        if r.status_code == 503:
            time.sleep(1)
            continue
        r.raise_for_status()

        last_etag = r.headers["etag"]

        if r.text == "NONE":
            maintenance_event = None
        else:
            maintenance_event = r.text

        if maintenance_event != last_maintenance_event:
            last_maintenance_event = maintenance_event
            callback(maintenance_event)


def maintenance_callback(event: Optional[str]) -> None:
    """
    Example callback function to handle the maintenance event.

    Args:
        event: details about scheduled maintenance.
    """
    if event:
        print(f"Undergoing host maintenance: {event}")
    else:
        print("Finished host maintenance")


def main():
    wait_for_maintenance(maintenance_callback)


if __name__ == "__main__":
    main()

出力を確認する

maintenance-event メタデータキーの初期値とデフォルト値は NONE です。

  • GPU を接続している VM の場合、メンテナンス イベント中に値が NONE から TERMINATE_ON_HOST_MAINTENANCE に変更されます。この値は、停止イベントの開始 60 分前に更新されます。

  • GPU のない VM でスケジュール オプションが migrate に設定されている場合、maintenance-event 値は次のように変更されます。

    1. マイグレーション イベントの開始時に、値は NONE から MIGRATE_ON_HOST_MAINTENANCE に変更されます。この値は、停止イベントの開始 60 秒前に更新されます。
    2. イベントの期間中、VM インスタンスがライブ マイグレーションされている間、値は MIGRATE_ON_HOST_MAINTENANCE のままとなります。
    3. メンテナンス イベントが終了すると NONE に戻ります。
  • 単一テナントノードでは、ホスト メンテナンス イベント中、maintenance-event メタデータ鍵の値は変更されず、イベントの開始から終了まで NONE のままになります。

次のステップ