500 Internal Server Error - ストリーミングが有効

Apigee Edge のドキュメントを表示しています。
Apigee X のドキュメントに移動します。
情報

症状

クライアント アプリケーションが、API 呼び出しに対して Internal Server Error というメッセージ付きの HTTP レスポンス ステータス コード 500 を受け取ります。

エラー メッセージ

クライアント アプリケーションは、次のようなエラー レスポンスを受け取ることがあります。

HTTP/1.1 500 Internal Server Error

この後に、次のようなエラー メッセージが表示されることがあります。

{
   "fault":{
      "faultstring":"Expecting } at line 1"
      "detail":{
         "errorcode":"Internal Server Error"
      }
   }
}

OR

{
   "fault":{
      "faultstring":"Expecting ] at line 1"
      "detail":{
         "errorcode":"Internal Server Error"
      }
   }
}

考えられる原因

500 Internal Server Error は、さまざまな原因で発生する可能性があります。このプレイブックでは、ストリーミングが有効な場合にリクエスト/レスポンス ペイロードにアクセスしたことが原因で発生する 500 Internal Server Error に焦点を当てています。

原因 説明 トラブルシューティング手順を実施できるユーザー
ストリーミングが有効な状態でペイロードにアクセスする ストリーミングが有効な場合にリクエスト/レスポンス ペイロードにアクセスすると、エラーが発生します。 Edge Private Cloud と Public Cloud のユーザー

原因: ストリーミングが有効な状態でペイロードにアクセスしている

診断

手順 1: トレースを使用する

  1. トレース セッションを有効にして、API 呼び出しを行い、500 Internal Server Error の問題を再現します。
  2. 失敗したリクエストのいずれかを選択し、トレースを確認します。
  3. トレースのさまざまなフェーズを確認し、障害が発生した場所を特定します。
  4. このエラーは、ポリシーがリクエスト/レスポンスのペイロードを解析しているときに発生することがあります。
  5. 次のトレースのスクリーンショットの例は、JSONThreatProtection ポリシーが 「Expecting } at line 1」というエラーで失敗していることを示しています。

    alt_text

    上記のスクリーンショットに示すように、トレース出力から次の情報をメモします。

    失敗したポリシー: JSONThreatProtection

    フロー: プロキシ リクエスト

  6. 失敗したポリシー定義を調べて、解析されているペイロードを確認します。

    このシナリオ例では、失敗した JSON-Threat-Protection という名前の JSONThreatProtection ポリシーを調べて、<Source> 要素を確認します。

    <JSONThreatProtection async="false" continueOnError="false" enabled="true" name="JSON-Threat-Protection">
       <DisplayName>JSON Threat Protection</DisplayName>
       <ArrayElementCount>20</ArrayElementCount>
       <ContainerDepth>10</ContainerDepth>
       <ObjectEntryCount>15</ObjectEntryCount>
       <ObjectEntryNameLength>50</ObjectEntryNameLength>
       <Source>request</Source>
       <StringValueLength>1000</StringValueLength>
    </JSONThreatProtection>

    <Source> 要素が request. を指していることに注意してください。これは、リクエスト ペイロードの解析中にエラーが発生したことを意味します。

  7. API リクエストをチェックして、解析されるペイロードのタイプを特定します。
  8. API リクエストで、リクエスト ペイロードと Content-Type ヘッダーの内容を確認できます。次の例の curl コマンドでは、JSON ペイロードが使用されています。

    curl -i https://VIRTUAL_HOST_ALIAS/BASEPATH -H "Content-Type: application/json" \
    -X POST -d @request-payload.json

    失敗しているポリシーを確認して、解析されているペイロードのタイプを特定することもできます。上記のシナリオの例では、JSON-Threat-Protection ポリシーが失敗しています。これは、ペイロードが JSON 形式である必要があることを示します。

  9. ペイロードの形式が正しいかどうかを検証します。ペイロードが無効な場合、このエラーが発生することがあります。

  10. ペイロードが有効であるにもかかわらず、エラー メッセージ セクションに記載されているエラーが発生する場合は、ストリーミングが有効になっているときにペイロードにアクセスしていることが原因です。

    ポリシーで解析されるペイロード(手順 6 で特定)に応じて、適切なフェーズで Trace ツール内のペイロードの内容を調べます。

    このシナリオ例では、リクエスト ペイロードが解析されているため、トレースの [Request Received from Client] フェーズを調べて、[Request Content] を確認します。

    alt_text

    有効なペイロードを送信したにもかかわらず、上記のスクリーンショットのように Request Content が空である場合は、この問題の原因はリクエスト ストリーミングが有効になっている可能性が高いことを示しています。

    これは、ストリーミングが有効になっている場合、リクエスト ペイロードがトレースに表示されないためです。

    同様に、エラー発生時にレスポンス ペイロードが解析されている場合は、「ターゲット サーバーから受信したレスポンス」フェーズでレスポンス コンテンツを確認します。

  11. 次に、API プロキシ フローで障害が発生したポリシーが使用されている場所に応じて、プロキシ エンドポイントとターゲット エンドポイントの定義を調べます。ストリーミングが有効になっているかどうかを確認します。

    このシナリオの例では、失敗したポリシーがプロキシ リクエスト フローで実行されました(上記の手順 5 で特定)。したがって、プロキシ エンドポイントを調べます。

    <ProxyEndpoint name="default">
    ...
      <HTTPProxyConnection>
        <BasePath>/v1/weather</BasePath>
        <VirtualHost>secure</VirtualHost>
        <Properties>
          <Property name="response.streaming.enabled">true</Property>
          <Property name="request.streaming.enabled">true</Property>
        </Properties>
      </HTTPProxyConnection>
    </ProxyEndpoint>

    上記の例に示すように、プロパティ "request.streaming.enabled" が true に設定されているため、リクエスト ストリーミングが有効になっています。

    したがって、エラーの原因は、ストリーミングが有効になっているときにリクエスト ペイロードにアクセスする API プロキシで JSONThreatProtection ポリシーを使用していることです。これにより、API プロキシでバッファリングがトリガーされ、Apigee Edge でストリーミングを使用する目的が果たせなくなるため、エラーが発生します。

    このエラーは、ペイロードが小さい場合は発生しないことがありますが、ペイロードが大きい場合は発生することがあります。

  12. 次の手順でトレースの 「AX」(分析データが記録された)フェーズの 「X-Apigee-fault-source」の値を確認することで、500 エラーがポリシーによって発生していることを確認できます。
    1. 下のスクリーンショットに示すように、["AX" (Analytics Data Recorded) Phase] をクリックします。

      alt_text

    2. フェーズの詳細を下にスクロールして [エラー ヘッダー] セクションを表示し、次の図に示すように、「X-Apigee-fault-code」「X-Apigee-fault-source」「X-Apigee-fault-policy」の値を特定します。

      alt_text

    3. 上の図に示すように、"X-Apigee-fault-source" の値が "policy" の場合、ストリーミングが有効になっているときにポリシーがペイロードにアクセスしたことが原因でエラーが発生したことを示します。

解決策

ストリーミングが有効な状態でペイロードにアクセスすることは、アンチパターン: ストリーミングが有効な場合にリクエスト/レスポンス ペイロードにアクセスするで説明したように、アンチパターンです。

  1. ペイロードを処理する場合は、次の例の ProxyEndpoint に示すように、プロパティ "request.streaming.enabled" and "response.streaming.enabled" を削除して、Proxy/Target Endpoint でストリーミングを無効にする必要があります。
    <ProxyEndpoint name="default">
    ...
      <HTTPProxyConnection>
        <BasePath>/v1/weather</BasePath>
        <VirtualHost>secure</VirtualHost>
      </HTTPProxyConnection>
    </ProxyEndpoint>

    または

  2. API プロキシでストリーミングを使用する場合は、リクエスト/レスポンス ペイロードにアクセスするポリシーを API プロキシで使用しないでください。

注:

  • このプレイブックでは、JSONThreatProtection ポリシーを使用して、ストリーミングが有効になっているリクエスト ペイロードを処理しました。これにより、さまざまなエラーで 500 Internal Server Error が発生しました。
  • このエラーは、ストリーミングが有効になっているときにリクエスト ペイロードまたはレスポンス ペイロードを処理する JSONToXML や XMLToJSON などのポリシーでも発生する可能性があります。
  • ストリーミングが有効になっているときにペイロードへのアクセスを必要とするプロキシでは、このようなポリシーを使用しないことを強くおすすめします。
  • これは、アンチパターン: ストリーミングが有効な場合にリクエスト/レスポンス ペイロードにアクセスするで説明されているように、アンチパターンです。

API Monitoring を使用して問題を診断する

Private Cloud ユーザーはこの手順をスキップしてください。

API Monitoring を使用すると、問題領域を迅速に切り分けて、エラー、パフォーマンス、レイテンシの問題とその発生元(デベロッパー アプリ、API プロキシ、バックエンド ターゲット、API プラットフォームなど)を診断できます。

API Monitoring を使用して API での 5xx 問題をトラブルシューティングする方法を説明するサンプル シナリオに従ってください。たとえば、500 エラーの数が特定のしきい値を超えたときに通知を行うようにアラートを設定します。

ポリシーから 500 エラー レスポンスがスローされたときに通知を受け取る場合は、障害ソースを [Proxy] に設定して、500 ステータス コードのアラートを設定する必要があります。

診断情報の収集が必要な場合

上記の手順でも問題が解決されない場合は、次の診断情報を収集してください。Apigee サポートに連絡して、収集した情報を提供してください。

Public Cloud をご利用の場合は、次の情報を提供してください。

  • 組織名
  • 環境名
  • API プロキシ名
  • 500 エラーを再現するための完全な curl コマンドとリクエスト ペイロード(存在する場合)
  • 500 Internal Server Error のリクエストを含むトレース ファイル
  • 現在 500 エラーが発生していない場合は、過去に 500 エラーが発生した期間とタイムゾーンの情報を提供します。

Private Cloud をご利用の場合は、次の情報を提供してください。

  • 失敗したリクエストで確認されたエラー メッセージの全文
  • 500 エラーが発生している組織、環境名、API プロキシ名
  • API プロキシ バンドル
  • リクエストで使用されたペイロード(ある場合)
  • 500 Internal Server Error のリクエストを含むトレース ファイル
  • NGINX アクセスログ(/opt/apigee/var/log/edge-router/nginx/ <org>~ <env>.<port#>_access_log
  • Message Processor ログ(/opt/apigee/var/log/edge-message-processor/logs/system.log
  • 500 エラーが発生した期間(タイムゾーン情報を含む)。