エラー処理

gRPCのエラー処理方法とgRPCエラーコード。

エラー処理

gRPCのエラー処理方法とgRPCエラーコード。

標準エラーモデル

コンセプトドキュメントと例で見たように、gRPC呼び出しが正常に完了すると、サーバーはクライアントに`OK`ステータスを返します(言語によっては、`OK`ステータスがコードで直接使用される場合と使用されない場合があります)。しかし、呼び出しが成功しなかった場合はどうなりますか?

エラーが発生した場合、gRPCは代わりにエラーステータスコードのいずれかを返します。オプションの文字列エラーメッセージには、発生した事象に関する詳細情報が提供されます。エラー情報は、サポートされているすべての言語のgRPCクライアントで利用できます。

リッチエラーモデル

上記のエラーモデルは公式のgRPCエラーモデルであり、すべてのgRPCクライアント/サーバーライブラリでサポートされており、gRPCデータ形式(プロトコルバッファなど)とは無関係です。お気づきかもしれませんが、これはかなり限定的であり、エラーの詳細を伝える機能は含まれていません。

ただし、データ形式としてプロトコルバッファを使用している場合は、こちらで説明されている、Googleによって開発および使用されているリッチエラーモデルの使用を検討することをお勧めします。このモデルにより、サーバーは1つ以上のprotobufメッセージとして表現された追加のエラー詳細を返し、クライアントはそれを消費できます。さらに、無効なパラメータ、クォータ違反、スタックトレースなど、最も一般的なニーズをカバーするための標準のエラーメッセージタイプのセットを指定しています。この追加のエラー情報のprotobufバイナリエンコーディングは、レスポンスのトレーリングメタデータとして提供されます。

このリッチエラーモデルは、C++、Go、Java、Python、およびRubyライブラリで既にサポートされており、少なくともgrpc-webおよびNode.jsライブラリには、それを要求する未解決の問題があります。他の言語ライブラリは、需要があれば将来的にサポートを追加する可能性があるため、興味がある場合はgithubリポジトリを確認してください。ただし、Cで記述されたgrpc-coreライブラリは、意図的にデータ形式に依存しないため、サポートされる可能性は低いことに注意してください。

プロトコルバッファを使用していない場合でも、同様のアプローチ(エラー詳細をトレーリングレスポンスメタデータに配置)を使用できますが、APIで実際に使用するには、このデータにアクセスするためのライブラリサポートを見つけるか、開発する必要があるでしょう。

ただし、このような拡張エラーモデルを使用するかどうかを決定する際には、以下の重要な考慮事項に注意する必要があります。

  • 拡張エラーモデルのライブラリ実装は、エラー詳細ペイロードの要件と期待値に関して、言語間で一貫していない場合があります
  • 既存のプロキシ、ロガー、およびその他の標準HTTPリクエストプロセッサは、エラー詳細を認識できないため、監視などの目的で活用できません
  • トレーラーに追加のエラー詳細があると、ヘッドオブラインブロッキングが妨げられ、キャッシュミスの頻度が高くなるため、HTTP/2ヘッダー圧縮効率が低下します
  • エラー詳細ペイロードが大きくなると、プロトコルの制限(最大ヘッダーサイズなど)に達する可能性があり、元のエラーが事実上失われます

エラーステータスコード

エラーは、ネットワーク障害から認証されていない接続まで、さまざまな状況でgRPCによって発生し、それぞれが特定のステータスコードに関連付けられています。次のエラーステータスコードは、すべてのgRPC言語でサポートされています。

一般的なエラー

ケースステータスコード
クライアントアプリケーションがリクエストをキャンセルしましたGRPC_STATUS_CANCELLED
サーバーがステータスを返す前にデッドラインが切れましたGRPC_STATUS_DEADLINE_EXCEEDED
サーバーでメソッドが見つかりませんGRPC_STATUS_UNIMPLEMENTED
サーバーがシャットダウンしていますGRPC_STATUS_UNAVAILABLE
サーバーが例外をスローしました(または、ステータスコードを返す以外の方法でRPCを終了しました)GRPC_STATUS_UNKNOWN

ネットワーク障害

ケースステータスコード
デッドラインが切れる前にデータが送信されませんでした。また、一部のデータが送信され、デッドラインが切れる前に他の障害が検出されなかった場合にも適用されますGRPC_STATUS_DEADLINE_EXCEEDED
接続が切断される前に、一部のデータが送信されました(たとえば、リクエストメタデータがTCP接続に書き込まれました)GRPC_STATUS_UNAVAILABLE

プロトコルエラー

ケースステータスコード
解凍できませんでしたが、圧縮アルゴリズムはサポートされていますGRPC_STATUS_INTERNAL
クライアントで使用されている圧縮メカニズムは、サーバーではサポートされていませんGRPC_STATUS_UNIMPLEMENTED
フロー制御リソース制限に達しましたGRPC_STATUS_RESOURCE_EXHAUSTED
フロー制御プロトコル違反GRPC_STATUS_INTERNAL
返されたステータスの解析エラーGRPC_STATUS_UNKNOWN
認証されていません:資格情報がメタデータを取得できませんでしたGRPC_STATUS_UNAUTHENTICATED
認証メタデータに無効なホストが設定されていますGRPC_STATUS_UNAUTHENTICATED
レスポンスプロトコルバッファの解析エラーGRPC_STATUS_INTERNAL
リクエストプロトコルバッファの解析エラーGRPC_STATUS_INTERNAL

言語サポート

標準エラーとリッチエラー詳細の処理方法に関するサンプルコードは、複数の言語で利用できます。

言語
C++C++エラー処理例
C++エラー詳細例
GoGoエラー処理例
Goエラー詳細例
JavaJavaエラー処理例
Javaエラー詳細例
NodeNodeエラー処理例
PythonPythonエラー詳細例

grpc-errorsリポジトリには、追加のエラー処理例も含まれています。