2

外部 API に対して 1 分あたり頻繁に (1000 以上) アウトバウンド接続を実行している WCF サービスがあります。

私のコードは次の例外を頻繁にスローしますが、WebException ステータス プロパティがReceiveFailureである WebException であることを常に示すとは限りません

送信リクエストを行うコードは次のとおりです。

HttpWebRequest request = (HttpWebRequest)WebRequest.Create(paramBuilder.ToString());
request.ServicePoint.ConnectionLeaseTimeout = 0;
request.Method = "GET";
request.Timeout = 33000;    //33 Second Timeout Is By Design
Stream stream = default(Stream);
HttpWebResponse response = default(HttpWebResponse);
try
{

    response = (HttpWebResponse) request.GetResponse();
    stream = response.GetResponseStream();
    reader = new StreamReader(stream,Encoding.UTF8);
    string str = reader.ReadToEnd();
    return str;

}
catch (WebException exception)
{

    //Handle WebException
}
catch (Exception exception)
{
    //Handle Exception
}
finally
{
    if (reader != null)
        reader.Dispose();

    if (response != null)
        response.Close();

    if (stream != null)
        stream.Dispose();
}

例外スタック トレースは、例外が GetResponse() から発生したことを示しています。

時折 WebException -ReceiveFailure を受け取ることが原因である可能性があります。

このステータスについては、MSDN のドキュメントを既に参照していますが、それは役に立ちません。

4

2 に答える 2

0

関連する問題があり、解決策を探しているときにいくつかのことに気付きました。

  • WebExceptionStatus enum呼び出した API が返した http ステータス コードと同等ではありません。代わりに、http 呼び出し中に発生する可能性のあるエラーの列挙です。
  • WebExceptionStatusAPI からエラー (400 から 599) を受け取ったときに返されるエラー コードは、WebExceptionStatus.ProtocolErrorint の 7 番です。
  • API から返された応答本文または実際の http ステータス コードを取得する必要がある場合は、まず is かどうかを確認する必要がありWebException.StatusますWebExceptionStatus.ProtocolError。次に、から実際の応答を取得して、WebExceptionStatus.Responseその内容を読み取ることができます。
  • タイムアウトは呼び出し元 (つまりコード) によって処理されることがあるため、その場合は応答がありません。だからあなたは見ることができWebException.StatusますWebExceptionStatus.Timeout

これは例です:

try
{
    ...
}
catch (WebException webException)
{
    if (webException.Status == WebExceptionStatus.ProtocolError)
    {
        var httpResponse = (HttpWebResponse)webException.Response;
        var responseText = "";
        using (var content = new StreamReader(httpResponse.GetResponseStream()))
        {
            responseText = content.ReadToEnd(); // Get response body as text
        }
        int statusCode = (int)httpResponse.StatusCode; // Get the status code
    }
    else if (webException.Status == WebExceptionStatus.ProtocolError)
    {
       // Timeout handled by your code. You do not have a response here.
    }

    // Handle other webException.Status errors. You do not have a response here.
}
于 2020-07-29T17:54:07.423 に答える