pull サブスクリプションのトラブルシューティング

このドキュメントでは、Pub/Sub pull サブスクリプションに関する一般的なトラブルシューティングのヒントを示します。pull サブスクリプションの詳細については、pull サブスクライバー ガイドをご覧ください。

Pub/Sub サブスクリプションを効果的にモニタリングするには、まず配信レイテンシの健全性スコアsubscription/delivery_latency_health_score)を確認して、どの要因が予期しないレイテンシの増加に貢献しているかを確認することをおすすめします。

最も古い未確認メッセージの経過時間が増加し続ける

oldest_unacked_message_age は、Pub/Sub サブスクリプションの健全性をモニタリングするための重要な指標です。サブスクライバーによってまだ確認応答(ack)されていない、サブスクリプションのバックログ内で最も古いメッセージの経過時間(秒単位)を測定します。この指標は、処理の遅延やボトルネックの可能性に関する貴重な分析情報を提供します。

メッセージ バックログをモニタリングすることで、メッセージをタイムリーかつ効率的に処理できます。最も古い未確認応答メッセージの経過時間を追跡することで、コンシューマーが遅延している状況を事前に特定できます。この方法により、パフォーマンスの低下に関連する潜在的な問題に早期に対処できます。

調査できる一般的なバックログの問題には、次のようなものがあります。

クライアント構成に関する問題

oldest_unacked_message_age 指標と num_undelivered_messages 指標の両方が同時に増加している場合は、サブスクライバーがメッセージの量についていけていない可能性があります。この状況では、サブスクライバー コンポーネントに焦点を当てて調査します。

  • クライアントの健全性: CPU、メモリ、ネットワーク帯域幅など、サブスクライバー クライアントをホストするマシンのリソース使用率を分析します。処理効率を妨げる可能性のあるプレッシャー ポイントを探します。

  • クライアント コード: 最近のコード変更を確認し、エラーログを調べます。サブスクライバー コードのバグや非効率性により、メッセージ処理率が大幅に低下する可能性があります。特定のメッセージに問題がある可能性があります。たとえば、複数のメッセージがデータベース内の同じ行に同時にアクセスする必要がある場合があります。この動作により、競合が発生し、レイテンシが高くなる可能性があります。

  • 割り当ての制限: ホスティング サービスによって課せられた Pub/Sub の割り当てまたは制限を超えていないことを確認します。サブスクライバーが Google Cloudでホストされている場合は、Compute Engine または GKE のリソース割り当てを確認して、潜在的なボトルネックを防ぎます。

サブスクライバーがメッセージを否定応答した

サブスクライバーがメッセージを否定応答(nack)すると、メッセージが正常に処理されなかったことが Pub/Sub に通知されます。Pub/Sub は同じメッセージの再配信を試みます。メッセージの nack を繰り返すと、重複が発生し、メッセージ配信の遅延が大きくなる可能性があります。

メッセージを nack しても、次の pull で別のメッセージが取得されるとは限りません。Pub/Sub の再配信ポリシーでは、新しいメッセージよりも先に nack されたメッセージが再配信されることがあります。したがって、特定のメッセージをフィルタリングまたはスキップする方法として nack に依存しないでください。代わりに、再試行ポリシー(できれば指数バックオフ)を設定して、後で処理できる可能性が高いが、再配信までに少し時間がかかる個々のメッセージをバックオフします。

特定のメッセージを意図的にスキップする必要がある場合は、処理しない場合でも、それらのメッセージを確認応答(ack)することをおすすめします。これにより、それらのアイテムはサブスクリプションから削除され、不要な再配信が回避され、リソースの消費が削減されます。メッセージを意図的に、または意図せずに未確認のままにすると、バックログの問題や配信の重複が発生します。

配信レイテンシが高い

Pub/Sub の配信レイテンシは、パブリッシャーからのメッセージがサブスクライバーに届くまでの時間です。配信レイテンシが高い原因として考えられるものについては、次のセクションで説明します。

チャンネル登録者数が少ない

StreamingPull を使用するクライアントの場合、常に低レイテンシを実現するには、サブスクリプションに対するオープンな StreamingPull 接続を複数保持します。アクティブなサブスクライバー接続がない場合、Pub/Sub はメッセージを迅速に配信できません。単一のストリームは単一障害点になる可能性があり、遅延のリスクが高まります。subscription/open_streaming_pulls 指標は、アクティブなストリーミング接続の数を示します。これを使用して、受信メッセージを処理するのに十分なストリームが常に確保されるようにします。

単項 pull を使用するクライアントの場合、常に低レイテンシを実現するには、サブスクリプションに対する未処理の pull リクエストを複数保持します。リクエストが少ないと、バックログにメッセージが蓄積され、レイテンシが増加する可能性があります。このアプローチにより、接続性のギャップを最小限に抑え、配信のレイテンシを改善できます。

高スループットと低レイテンシを必要とし、運用オーバーヘッドと処理コストを最小限に抑える必要がある場合は、高レベルのクライアント ライブラリをおすすめします。デフォルトでは、高レベル クライアント ライブラリは StreamingPull API を使用します。これは、レイテンシを最小限に抑えるのに適しているためです。高レベル クライアント ライブラリには、認証、スループット、レイテンシの最適化、メッセージのフォーマットなどの機能のために基盤となる API 呼び出しを処理するビルド済み関数とクラスが含まれています。

クライアント構成に関する問題

クライアント構成の問題をご覧ください。

バックログが多い

Pub/Sub サブスクリプションの未確認のメッセージのメッセージ バックログは、メッセージがサブスクライバーによってすぐに処理されないため、エンドツーエンドのレイテンシを本質的に増加させます。

順序指定キーと 1 回限りの配信

順序付けキーと 1 回限りの配信は便利な機能ですが、正しい配信を保証するには、Pub/Sub 内で追加の調整が必要です。この調整により、可用性が低下し、レイテンシが増加する可能性があります。定常状態では差は最小限ですが、必要な調整手順によってレイテンシが一時的に増加したり、エラー率が増加したりする可能性があります。順序指定が有効になっている場合、順序指定キーを持つメッセージは、同じ順序指定キーを持つ以前のメッセージが ACK されるまで配信できません。

メッセージの順序付けや 1 回限りの配信がアプリケーションに不可欠かどうかを検討します。レイテンシの短縮が最優先事項である場合は、これらの機能の使用を最小限に抑えることで、メッセージ処理の遅延を短縮できます。

メッセージ サイズの増加

メッセージ サイズが急増すると、Pub/Sub とクライアントとの間の転送時間が長くなり、クライアント側でのメッセージの処理時間が長くなる可能性があります。

配信レイテンシの増加が見られる場合は、topic/message_sizes 指標を使用してメッセージ サイズを確認し、topic_id でグループ化できます。メッセージ サイズの急増とパフォーマンスの問題を関連付けます。

メッセージが見つからない

メッセージが購読者に正常に配信されていないと思われる場合は、次のいずれかの理由が考えられます。

複数のコンシューマーを含む Pub/Sub サブスクリプションでのメッセージ配信

Pub/Sub では、メッセージがコンシューマー間で不均等に分散されることがあります。この動作は、Pub/Sub が効率を高めるためにアクティブなコンシューマー間でメッセージを分散するために発生します。場合によっては、1 人のコンシューマが、想定よりも少ないメッセージや、他のコンシューマとは異なるメッセージのサブセットを受信することもあります。

メッセージはすでにクライアントに届いている可能性があり、未確認のメッセージのバックログがあるからといって、必ずしも次の pull リクエストでそれらのメッセージを受け取れるとは限らないことに注意してください。コンシューマーは、 Google Cloud コンソールまたは Google Cloud CLI で pull を使用しているか、カスタム サブスクライバーをローカルで実行してメッセージを確認している場合があります。

単項 Pull クライアントの場合、一部の pull リクエストでメッセージが返されないことがあります。サブスクライバーが足りないセクションで説明したように、一部のリクエストでは、構成された最大メッセージ数より少ないメッセージが返される場合や、メッセージが返されない場合があるため、未処理の pull リクエストを複数保持することをおすすめします。

このような動作が疑われる場合は、サブスクリプションに同時に接続されているコンシューマーが複数あるかどうかを調査し、それらを検査します。

サブスクリプションでフィルタする

サブスクリプションにフィルタが関連付けられているかどうかを確認します。その場合、フィルタに一致するメッセージのみを受信します。Pub/Sub サービスは、フィルタに一致しないメッセージの確認応答を自動的に行います。フィルタがバックログ指標に与える影響を考慮します。

オプション returnImmediately を使用する

クライアントが単項 Pull を使用している場合は、returnImmediately フィールドが true に設定されているかどうかを確認します。これは非推奨のフィールドです。このフィールドは、メッセージが返されなくても pull リクエストに直ちに応答するよう Pub/Sub サービスに指示します。これにより、バックログがある場合でも、プルリクエストが 0 件のメッセージで返されることがあります。

重複の処理

Pub/Sub でのメッセージの重複は、サブスクライバーが確認応答期限内にメッセージを確認応答できない場合に発生することがよくあります。これにより、メッセージが再配信され、重複しているように見えます。subscription/expired_ack_deadlines_count 指標を使用して、サブスクライバーが確認応答期限に間に合わないレートを測定できます。詳しくは、確認期限の終了をモニタリングするをご覧ください。

メッセージの期限を延長すると、重複率を低下させることができます。

  • 期限の延長はクライアント ライブラリによって自動的に処理されますが、構成可能な延長期限の最大値にはデフォルトの上限があります。
  • 独自のクライアント ライブラリを構築する場合は、modifyAckDeadline メソッドを使用して、確認応答期限を延長します。

メッセージが処理および確認応答されるよりも速くサブスクライバーに pull されると、一部のメッセージが期限切れになり、期限の延長が必要になることがあります。ただし、サブスクライバーの負荷が軽減されない場合、期限の延長を繰り返しても最終的には失敗します。最悪の場合、サブスクライバーが重複で溢れ、バックログが悪化する可能性があります。有効期限が切れた重複が、新しい重複を生成します。

サブスクライバーに過負荷がかからないようにするには、サブスクライバーが一度に取得するメッセージの数を減らします。これにより、サブスクライバーが期限内に処理するメッセージの数を減らすことができます。有効期限切れのメッセージと再配信されるメッセージが少なくなります。

サブスクライバーが一度に取得するメッセージの数を減らすには、サブスクライバーのフロー制御構成で未処理のメッセージの最大数を減らす必要があります。万能な値はないため、スループットとサブスクライバー容量に基づいて最大未処理メッセージ数の上限を調整する必要があります。各アプリケーションはメッセージを異なる方法で処理し、メッセージの確認応答に異なる時間を要します。

再試行を強制する

Pub/Sub にメッセージの再試行を強制するには、nack リクエストを送信します。高レベルのクライアント ライブラリを使用していない場合は、ackDeadlineSeconds を 0 に設定して modifyAckDeadline リクエストを送信します。

順序指定キー

Pub/Sub は、順序指定キーを含むメッセージを再配信するときに、同じ順序指定キーを持つ後続のメッセージ(以前に確認応答されたメッセージを含む)もすべて再配信します。これは、シーケンスの順序を保持するために行われます。ただし、依存メッセージがシーケンス内の前のメッセージの ack が成功した後にのみ送信されるという厳密な保証はありません。

サブスクライバーがメッセージを否定応答している

サブスクライバーがメッセージを否定応答しているをご覧ください。

StreamingPull サブスクリプションのトラブルシューティング

リクエスト レイテンシ指標とエンドツーエンドの配信レイテンシの関係

StreamingPull の場合、指標 serviceruntime.googleapis.com/api/request_latencies は、ストリームが開いている時間を表します。この指標は、エンドツーエンドの配信レイテンシを判断するうえで役に立ちません。

リクエスト レイテンシ指標を使用する代わりに、配信レイテンシの健全性スコアを使用して、エンドツーエンドの配信レイテンシの増加の原因となっている要因を確認します。

StreamingPull 接続が OK 以外のステータスで終了する

StreamingPull ストリームは、常に OK 以外のステータスで終了します。単一 RPC のエラー ステータスとは異なり、StreamingPull のこのステータスは、ストリームが切断されたことを示しています。リクエストは失敗していません。そのため、StreamingPull API のエラー率が 100% にもなることがありますが、この動作は設計によるものです。

StreamingPull ストリームは常にエラーで終了するため、エラーの診断中にストリーム終了の指標を調べることは役に立ちません。代わりに、response_code または response_class でグループ化された StreamingPull レスポンス指標 subscription/streaming_pull_response_count を重視します。

次のエラーを探します。

  • サブスクリプション バックログに無効な Cloud KMS 鍵で暗号化されたメッセージがある場合、前提条件失敗エラーが発生することがあります。プルを再開するには、鍵へのアクセスを復元します。

  • Pub/Sub でリクエストを処理できないときに発生する可能性のある使用不可のエラー。これは一時的な状態である可能性が高く、クライアント ライブラリはリクエストを再試行します。クライアント ライブラリを使用している場合は、対応は必要ありません。

  • 存在しないエラーは、サブスクリプションが削除された場合、またはサブスクリプションが最初から存在しなかった場合に発生する可能性があります。後者のケースは、無効なサブスクリプション パスを指定した場合に発生します。

その他の関連情報