このガイドでは、Knative serving サービスで Webhook ターゲットをホストする方法について説明します。
Cloud Run 関数と Knative serving
Cloud Run 関数と Knative serving はどちらも、Webhook ターゲットをホストするための優れたソリューションを提供します。一般に、Cloud Run 関数は設定が簡単で、プロトタイピングに適していており、ワークフローの量が少ないときに最適です。Knative serving は柔軟性が高く、大量のボリュームを同時実行で処理できます。
次の場合は Knative serving を使用します。
- Cloud Run 関数でサポートされていない言語またはランタイムを使用している
- リクエスト タイムアウトの延長が必要(最大 15 分)
- 大容量を想定しており、同時実行が必要(コンテナ インスタンスあたり 80 件の同時リクエスト)
Knative serving での Webhook ターゲットの作成
Knative serving を使用すると、任意の言語で Webhook ターゲットを定義できます。必要なのは、データを受け入れることができる HTTP エンドポイントを作成することだけです。通常、これには POST
を使用します。
@app.route('/', methods=['POST'])
def index():
data = request.get_json()
上記の例では、URL のインデックス ページは POST
リクエストのみを受け入れるように構成されており、データは JSON ペイロードを介して配信されます。
Webhook プロバイダとの統合
HTTP コールバックを提供するほとんどのサービスでは、URL の所有権を確認する必要があります。通常は、なんらかのトークン、メッセージ、またはシークレットを送信し、有効なレスポンスが返されるかどうか検証することで、所有権を確認します。これらの要件はサービス プロバイダから取得する必要があります。上記と同じ例では、次のようになります。
def index():
data = request.get_json()
return data['challenge']
プロバイダが所有権を確認したら、ユーザー側でも承認を追加する必要があります。
リクエストの承認
Webhook ターゲットはオープンな公開 URL です。ほとんどのサービスは、受信リクエストが承認済みのサービスからのものであることを確認するためにトークンまたはシークレットを提供します。URL は公開されているため、Webhook ターゲットへデータを送信しようとする悪意のある試みを防ぐことはできません。ただし、トークンまたはシークレットを使用すると、承認されたソースからのデータのみを処理するようにできます。
リクエストを確認するには、シークレットを構成するか、シークレットのコピーを環境変数として保存するか、なんらかの鍵管理システムを使用して保存します。
シークレットのコピーを環境変数として保存する場合、各リクエストでリクエスト ヘッダーまたは JSON ペイロードにシークレットまたはトークンが含まれている必要があります。また、それをチェックしてソースが有効であることを確認する必要もあります。
def index():
request_secret = request.headers['Secret']
if request_secret != os.environ['SECRET']:
return ('Unauthorized', 401)
Webhook プロバイダがシークレットまたはその他の認証メカニズムをサポートしていない場合、Webhook ターゲットの URL を持つすべてのユーザーがメッセージを送信できます。この場合、Webhook の実装を公共のインターネットに公開しても安全上の問題はありません。
リクエストへの応答
ほとんどのサービスでは、サービスで指定された時間内にリクエストに応答する必要があります。一部の Webhook には、再試行メソッドが組み込まれています。HTTP ステータス コード 4xx や 5xx などのエラー レスポンスが発生した場合は、成功のステータス コード(2xx)を返して、イベントが正しく処理されたことをサービスが正しく認識できるようにする必要があります。
def index():
data = request.get_json()
return ('', 200)
タイムアウト
Knative serving と Webhook プロバイダの両方にタイムアウトがあります。2 つのうち短い方がアプリケーションに適用されます。データ処理が Knative serving または Webhook プロバイダによって割り当てられた時間を超える場合は、Pub/Sub や Cloud Tasks など、処理を非同期で完了することを許可するプロダクトを使用する必要があります。これらのプロダクトを使用すると、データを迅速に引き渡し、すぐに Webhook プロバイダに成功レスポンスを返して、タイムアウトの心配なく処理を続行できます。これらは失敗や再試行の処理にも適しています。
一般的な Webhook パターン
型 | 例 |
---|---|
データのリレー | Webhook が呼び出されるたびに Firebase Cloud Messaging を介して通知を送信します。 |
データの保存 | データを BigQuery に保存し、後で分析します。 |
アクションのトリガー | GitHub で新しいコードが commit されるたびに、Dialogflow でのアクションの実行、Twitter への返信の投稿、ステージング環境への push を行います。 |
次のステップ
- Cloud Run 関数での Webhook(HTTP トリガー)の詳細を確認する
- Google Cloud Observability で Webhook 通知を設定する
- push サブスクリプションを使用して Webhook に Pub/Sub メッセージを送信する
- Dialogflow で Webhook を使用してアクションを実行する