【问题标题】:The underlying connection was closed exception while WebClient DownloadStringWebClient DownloadString 时底层连接被关闭异常
【发布时间】:2016-03-31 23:23:04
【问题描述】:

一段代码

WebClient wc = new WebClient();
String str = wc.DownloadString(new Uri("http://content.warframe.com/dynamic/rss.php"));

我遇到了异常:

“System.Net.WebException”类型的未处理异常发生在 系统.dll

附加信息:底层连接已关闭: 连接意外关闭。

我认为这是 .NET 中的一个错误(我使用的是 3.5),但我尝试了其他方法来获取此链接的内容(其 rss、xml)。还没有幸运的一击

var webrequest = (WebRequest)HttpWebRequest.Create(@"http://content.warframe.com/dynamic/rss.php");
var resp = webrequest.GetResponse();
//HttpWebResponse webresponse = (HttpWebResponse)webrequest.GetResponse(); // Wont work also

上面的这段代码也不行,都抛出了同样的异常

提琴手日志:

会话状态:已中止。
响应实体大小:512 字节。

== 旗帜 ===================
BitFlags:[ResponseGeneratedByFiddler] 0x100
X-ABORTED-WHEN:完成
X-CLIENTIP:127.0.0.1
X-CLIENTPORT:2747
X-出口:2748
X-FAILSESSION-WHEN:阅读响应
X-HOSTIP:205.185.216.10
X-PROCESSINFO: willitwork.vshost:3300

== 时间信息 ============
客户端连接:10:29:11.706
客户端开始请求:10:29:11.713
GotRequestHeaders:10:29:11.713
ClientDoneRequest:10:29:11.713
确定网关:0ms
DNS 查找:164 毫秒
TCP/IP 连接:74 毫秒
HTTPS 握手:0 毫秒
服务器已连接:10:29:11.953
FiddlerBeginRequest:10:29:11.953
服务器获得请求:10:29:11.953
服务器开始响应:10:29:12.372
GotResponseHeaders:00:00:00.000
服务器完成响应:10:29:12.372
客户端开始响应:10:29:12.385
ClientDoneResponse:10:29:12.385

总经过时间:0:00:00.672

响应在传递给客户端之前被缓冲。

== WININET 缓存信息 =============
WinINET 缓存中不存在此 URL。 [代码:2]
* 注意:以上数据显示的是 WinINET 当前的缓存状态,而不是请求时的状态。
* 注意:以上数据仅显示 WinINET 的中等完整性(非保护模式)缓存​​。

另外 - 504,这没有意义,因为我可以通过 chrome / firefox / ie 从链接获取数据...

我只是为了用其他语言工作,但我不得不用 C# 来做(我已经写了 2 个代码来重写它)

我添加了一些设置,比如提琴手说的

myHttpWebRequest1.ProtocolVersion = HttpVersion.Version11;
myHttpWebRequest1.UserAgent = "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/35.0.1916.153 Safari/537.36";
myHttpWebRequest1.Accept = "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8";

至少现在我得到 504 错误而不是“未知”,但我仍然可以通过 webbrowser 查看内容,所以 504 错误是假的

编辑:我添加时没有响应错误

myHttpWebRequest1.Headers["Accept-Encoding"] = "gzip";

但现在输出混乱且不可读

【问题讨论】:

  • 不要过早断定这是一个 BCL 错误。更改请求标头会导致不同的错误这一事实有力地证明了服务器只是不喜欢您发送的内容。
  • 我正在尝试发送我的网络浏览器发送的内容(至少是标题)。我始终遵循代码按照您编写的方式运行的规则。
  • 安装补丁 support.microsoft.com/en-us/kb/3042058 后,我们在 .Net Framework 3.5 下使用 SSL (TLS 1.0) 时收到此消息。删除更新解决了问题。

标签: c# webclient downloadstring


【解决方案1】:

我有同样的错误。

您可以将 User Agent 添加到您的 httpRequest

request.UserAgent = "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/535.2 (KHTML, like Gecko) Chrome/15.0.874.121 Safari/535.2";

【讨论】:

    【解决方案2】:

    好的,我得到了所有的修复和工作!

    static void Main(string[] args)
    {
        Uri url = new Uri(@"http://content.warframe.com/dynamic/rss.php");
    
        HttpWebRequest request = (HttpWebRequest)WebRequest.Create(url);
    
        // MAGIC LINE GOES HERE \/
        request.AutomaticDecompression = DecompressionMethods.GZip | DecompressionMethods.Deflate;
    
        // Assign the response object of HttpWebRequest to a HttpWebResponse variable.
        using (HttpWebResponse response = (HttpWebResponse)request.GetResponse())
        {
            using (Stream streamResponse = response.GetResponseStream())
            {
                using (StreamReader streamRead = new StreamReader(streamResponse))
                {
                    Char[] readBuff = new Char[2000];
                    int count = streamRead.Read(readBuff, 0, 2000);
                    while (count > 0)
                    {
                        String outputData = new String(readBuff, 0, count);
                        Console.Write(outputData);
                        count = streamRead.Read(readBuff, 0, 2000);
                    }
                }
            }
        }
    
        Console.ReadKey();
    }
    

    除了不使用 WebClient.DownloadString 方法之外,我还必须添加 decompression

    request.AutomaticDecompression = DecompressionMethods.GZip | DecompressionMethods.Deflate;
    

    感谢提示(尤其是提琴手一号,解码按钮节省了我查找问题的时间)

    【讨论】:

    • 你知道我的家用电脑上的代码怎么可能没有任何问题而你必须解压缩?它是公共网站,所以它对我和你的工作方式应该相同?
    • 我认为它必须在客户端配置,我正在寻找答案,我只找到了有关 IIS 配置的注释。由于在 Windows 7 中我没有默认安装 IIS,所以我手动安装了它,这表明我没有安装用于动态压缩的模块(在本例中为 php)。我不是网络方面的专家,我认为 IIS 不是寻找答案的地方......
    • 对我不起作用。我仍然得到:底层连接已关闭:发送时发生意外错误。 InnerException = {"身份验证失败,因为远程方已关闭传输流。"}
    【解决方案3】:

    检查这个答案:

    ..The underlying connection was closed: An unexpected error occurred on a receive

    所以这可能对你有用:

    var webRequest = (HttpWebRequest)HttpWebRequest.Create(@"http://content.warframe.com/dynamic/rss.php");
    webRequest.KeepAlive = false;
    var resp = webRequest.GetResponse();        
    

    编辑:

    您是对的,请检查以下内容: http://msdn.microsoft.com/cs-cz/library/system.net.httpwebrequest.keepalive%28v=vs.110%29.aspx

    这是打印收到的响应内容的工作代码:

        static void Main(string[] args)
        {
              // Create a new HttpWebRequest object.Make sure that 
              // a default proxy is set if you are behind a firewall.
              HttpWebRequest myHttpWebRequest1 =
                (HttpWebRequest)WebRequest.Create(@"http://content.warframe.com/dynamic/rss.php");
    
              myHttpWebRequest1.KeepAlive=false;
              // Assign the response object of HttpWebRequest to a HttpWebResponse variable.
              HttpWebResponse myHttpWebResponse1 = 
                (HttpWebResponse)myHttpWebRequest1.GetResponse();
    
              Console.WriteLine("\nThe HTTP request Headers for the first request are: \n{0}", myHttpWebRequest1.Headers);
    
              Stream streamResponse = myHttpWebResponse1.GetResponseStream();
              StreamReader streamRead = new StreamReader(streamResponse);
              Char[] readBuff = new Char[256];
              int count = streamRead.Read(readBuff, 0, 256);
              Console.WriteLine("The contents of the Html page are.......\n");
              while (count > 0)
              {
                  String outputData = new String(readBuff, 0, count);
                  Console.Write(outputData);
                  count = streamRead.Read(readBuff, 0, 256);
              }
              Console.WriteLine();
              // Close the Stream object.
              streamResponse.Close();
              streamRead.Close();
              Console.ReadKey();
        }
    

    【讨论】:

    • WebRequest 没有 KeepAlive 方法,链接没有帮助我因为我不明白如何将他的代码实现到我的中
    • 不,仍然无法正常工作。我已经关闭了防火墙,在未关闭的流的情况下重新启动了我的计算机,我什至更改了我的 IP ......仍然是同样的问题。 GetResponse() 失败
    • 在我的电脑上,这段代码可以像你一样使用 .NET 3.5 完美运行。看来您的问题出在其他地方。您是否使用普通浏览器得到响应?如果是,请尝试使用上面提供的代码制作简单的控制台应用程序,看看它是否正常工作。也尝试添加 myHttpWebRequest1.ProtocolVersion=HttpVersion.Version10;
    • 另一种选择是使用 Fiddler 调试您的请求。
    • 我在谷歌上搜索提琴手,但我必须学习一点它在我的电脑、笔记本电脑和朋友的电脑上不起作用,但这可能是编译错误或……
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2023-03-27
    • 1970-01-01
    • 2014-05-31
    • 2010-09-22
    • 2012-04-26
    • 1970-01-01
    相关资源
    最近更新 更多