当前位置:  开发笔记 > 编程语言 > 正文

.Net HttpWebRequest.GetResponse()在返回http状态代码400(错误请求)时引发异常

如何解决《.NetHttpWebRequest.GetResponse()在返回http状态代码400(错误请求)时引发异常》经验,为你挑选了5个好方法。

我遇到的情况是,当我从服务器获取HTTP 400代码时,服务器告诉我我的请求有什么问题(使用HTTP响应内容中的消息)是完全合法的方式

但是,当状态代码为400时,.NET HttpWebRequest会引发异常.

我该如何处理?对我来说,400是完全合法的,而且非常有帮助.HTTP内容有一些重要的信息,但异常使我离开了我的道路.



1> Jon Skeet..:

如果有某种方法可以关闭"抛出非成功代码",那将会很好,但是如果你捕获WebException,你至少可以使用响应:

using System;
using System.IO;
using System.Web;
using System.Net;

public class Test
{
    static void Main()
    {
        WebRequest request = WebRequest.Create("http://csharpindepth.com/asd");
        try
        {
            using (WebResponse response = request.GetResponse())
            {
                Console.WriteLine("Won't get here");
            }
        }
        catch (WebException e)
        {
            using (WebResponse response = e.Response)
            {
                HttpWebResponse httpResponse = (HttpWebResponse) response;
                Console.WriteLine("Error code: {0}", httpResponse.StatusCode);
                using (Stream data = response.GetResponseStream())
                using (var reader = new StreamReader(data))
                {
                    string text = reader.ReadToEnd();
                    Console.WriteLine(text);
                }
            }
        }
    }
}

你可能想在一个单独的方法中封装"让我得到一个响应,即使它不是成功代码".(如果没有回复,我建议你仍然扔,例如,如果你无法连接.)

如果错误响应可能很大(这是不寻常的),您可能需要调整HttpWebRequest.DefaultMaximumErrorResponseLength以确保获得整个错误.


GetResponseStream()在附加到WebException的响应上返回的流的内容只是状态代码的名称(例如"错误请求"),而不是服务器实际返回的响应.有没有办法获得这些信息?

2> Matthew..:

我知道很久以前就已经回答了这个问题,但我做了一个扩展方法,希望能帮助其他人来解决这个问题.

码:

public static class WebRequestExtensions
{
    public static WebResponse GetResponseWithoutException(this WebRequest request)
    {
        if (request == null)
        {
            throw new ArgumentNullException("request");
        }

        try
        {
            return request.GetResponse();
        }
        catch (WebException e)
        {
            if (e.Response == null)
            {
                throw;
            }

            return e.Response;
        }
    }
}

用法:

var request = (HttpWebRequest)WebRequest.CreateHttp("http://invalidurl.com");

//... (initialize more fields)

using (var response = (HttpWebResponse)request.GetResponseWithoutException())
{
    Console.WriteLine("I got Http Status Code: {0}", response.StatusCode);
}



3> 小智..:

有趣的是HttpWebResponse.GetResponseStream(),您从中获得WebException.Response的与您从服务器收到的响应流不同.在我们的环境中,当使用对象将400 HTTP状态代码返回给客户端时,我们将丢失实际的服务器响应HttpWebRequest/HttpWebResponse.从我们所看到的,与该关联的响应流WebException's HttpWebResponse在客户端生成,并且不包括来自服务器的任何响应主体.非常令人沮丧,因为我们想要向客户端发回错误请求的原因.



4> Jugglist..:

尝试连接到Google的OAuth2服务时,我遇到了类似的问题.

我最终手动编写POST,而不是使用WebRequest,如下所示:

TcpClient client = new TcpClient("accounts.google.com", 443);
Stream netStream = client.GetStream();
SslStream sslStream = new SslStream(netStream);
sslStream.AuthenticateAsClient("accounts.google.com");

{
    byte[] contentAsBytes = Encoding.ASCII.GetBytes(content.ToString());

    StringBuilder msg = new StringBuilder();
    msg.AppendLine("POST /o/oauth2/token HTTP/1.1");
    msg.AppendLine("Host: accounts.google.com");
    msg.AppendLine("Content-Type: application/x-www-form-urlencoded");
    msg.AppendLine("Content-Length: " + contentAsBytes.Length.ToString());
    msg.AppendLine("");
    Debug.WriteLine("Request");
    Debug.WriteLine(msg.ToString());
    Debug.WriteLine(content.ToString());

    byte[] headerAsBytes = Encoding.ASCII.GetBytes(msg.ToString());
    sslStream.Write(headerAsBytes);
    sslStream.Write(contentAsBytes);
}

Debug.WriteLine("Response");

StreamReader reader = new StreamReader(sslStream);
while (true)
{  // Print the response line by line to the debug stream for inspection.
    string line = reader.ReadLine();
    if (line == null) break;
    Debug.WriteLine(line);
}

写入响应流的响应包含您所追踪的特定错误文本.

特别是,我的问题是我在URL编码的数据片段之间放置了端点.当我拿出它们时,一切正常.您可以使用类似的技术连接到您的服务并阅读实际的响应错误文本.


HttpWebRequest太混乱了。甚至套接字也更容易使用(因为它们不会向您隐藏错误)。

5> 小智..:

试试这个(这是VB代码:-):

Try

Catch exp As WebException
  Dim sResponse As String = New StreamReader(exp.Response.GetResponseStream()).ReadToEnd
End Try

推荐阅读
女女的家_747
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有