公司[1]一牛人看我的代码,说我设置的timeout有误,还应该设置ReadWriteTimeout。本人很不服,于是上网查看了相关说明。
HttpWebRequest httpWebRequest = WebRequest.CreateHttp("http://www.kangry.net");
httpWebRequest.ReadWriteTimeout = ;
httpWebRequest.Timeout = ;

MSDN对ReadWriteTimeout的说明如下:

在写入由 GetRequestStream 方法返回的流时,或在读取由 GetResponseStream 方法返回的流时,会用到 ReadWriteTimeout 属性。
具体而言,ReadWriteTimeout 属性控制 Read 方法(用来读取由 GetResponseStream 方法返回的流)和 Write 方法(用来写入由 GetRequestStream 方法返回的流)的超时。
若要指定等待请求完成的时间量,请使用 Timeout 属性[2]。
MSDN对Timeout的说明如下:
Timeout 是进行后续同步请求时使用 GetResponse 方法等待响应以及 GetRequestStream 方法等待流所允许的毫秒数。 Timeout 适用于整个请求和响应,不单独对GetRequestStream 与 GetResponse 方法调用响应。 如果资源在超时期限内未返回,请求将引发 WebException,并将 Status 属性设置为 WebExceptionStatus.Timeout。
Timeout 属性必须在 GetRequestStream 或 GetResponse 方法被调用之前设置。 在调用 GetRequestStream 或 GetResponse 方法之后更改 Timeout 属性不起任何作用
Timeout 属性对使用 BeginGetResponse 或 BeginGetRequestStream 方法生成的异步请求无效[3]。

通俗一点说,Timeout设置的是从发出请求开始算起,到与服务器建立连接后收到Http响应头的时间。ReadWriteTimeout设置的是从建立连接开始,到下载数据完毕所历经的时间。
   
以下一个例子可以说明这个问题[4]。
首先是抓取的代码:
HttpWebRequest req = (HttpWebRequest)WebRequest.Create("http://www.kangry.net/Home/t1");
req.Timeout = ; //设置超时时间为5秒 Stopwatch timer = new Stopwatch();
timer.Start(); string data;
HttpWebResponse resp = (HttpWebResponse)req.GetResponse();
using (StreamReader reader = new StreamReader(resp.GetResponseStream(), System.Text.Encoding.UTF8))
{
data = reader.ReadToEnd();
} timer.Stop(); Console.Write(data + "\r\n" + timer.Elapsed.TotalSeconds.ToString() + "\r\n");

其中我做了几个页面,分别是”t1″、“t2”、“t3”、“t4”。

其中t1页面直接返回文本内容,用作基础对照。
t2页面设置了一个延时,但是延时时间在超时的范围内。
t3页面设置了一个延时,但是延时时间超过抓取程序的timeout时间。
t4页面首先是先往客户端发送一部分内容,然后延时一段比timeout更长的时间,模拟出网速很慢的样子,再把剩下的字符串发送完毕。
代码如下:

public ActionResult t1()
{
return Content("直接返回内容。");
} public ActionResult t2()
{
System.Threading.Thread.Sleep();
return Content("休息了3秒");
} public ActionResult t3()
{
System.Threading.Thread.Sleep();
return Content("休息了7秒");
} public ActionResult t4()
{
using (var streamWriter = new StreamWriter(Response.Body, System.Text.Encoding.UTF8))
{
streamWriter.Write("hello"); //调用StreamWriter的Flush方法后,Http响应头和上面的字符串"hello"就会发送给客户端了
streamWriter.Flush(); System.Threading.Thread.Sleep();
streamWriter.Write("Kangry");
} //如果不使用StreamWriter,也可以用Response.Body.Write方法来写入数据到Http响应
//using (Response.Body)
//{
// byte[] data = System.Text.Encoding.UTF8.GetBytes("hello");
// Response.Body.Write(data, 0, data.Length); // //调用Response.Body.Flush方法后,Http响应头和字符串"hello"就会发送给客户端了
// Response.Body.Flush(); // System.Threading.Thread.Sleep(8000); // data = System.Text.Encoding.UTF8.GetBytes("Kangry");
// Response.Body.Write(data, 0, data.Length);
// Response.Body.Flush();
//} return new EmptyResult();
}

测试的结果是:

t1很快返回内容,且没有错误。
t2在3秒后也返回了内容,且没有错误。
t3在5秒后客户端抛出timeout的错误。
t4在8秒后返回内容,并没有出现错误。
根据测试结果,timeout设置的时间并不包括数据下载所耗费的时间。
MS的牛人果然牛,得多多向他学习!
 

原文链接

HttpWebRequest的timeout和ReadWriteTimeout(转载)的更多相关文章

  1. HttpWebRequest的Timeout和ReadWriteTimeout

    HttpWebRequest.Timeout在发起请求开始,如果未从远程请求的URL得到任何数据的情况下,超过Timeout后,触发超时异常 HttpWebRequest.ReadWriteTimeo ...

  2. HttpWebRequest's Timeout and ReadWriteTimeout — What do these mean for the underlying TCP connection?

    http://stackoverflow.com/questions/7250983/httpwebrequests-timeout-and-readwritetimeout-what-do-thes ...

  3. 【转载】HttpWebRequest的GetResponse或GetRequestStream偶尔超时 + 总结各种超时死掉的可能和相应的解决办法

    [问题] 用C#模拟网页登陆,其中去请求几个页面,会发起对应的http的请求request,其中keepAlive设置为true,提交请求后,然后会有对应的response: resp = (Http ...

  4. HttpWebRequest 模拟浏览器访问网站

    最近抓网页时报错: 要么返回 The remote server returned an error: (442)要么返回: 非法访问,您的行为已被WAF系统记录! 想了想,就当是人家加了抓网页的东西 ...

  5. 【已解决】HttpWebRequest的GetResponse或GetRequestStream偶尔超时 + 总结各种超时死掉的可能和相应的解决办法

    [问题] 用C#模拟网页登陆,其中去请求几个页面,会发起对应的http的请求request,其中keepAlive设置为true,提交请求后,然后会有对应的response: resp = (Http ...

  6. HttpWebRequest的GetResponse或GetRequestStream偶尔超时 + 总结各种超时死掉的可能和相应的解决办法

    [问题] 用C#模拟网页登陆,其中去请求几个页面,会发起对应的http的请求request,其中keepAlive设置为true,提交请求后,然后会有对应的response: resp = (Http ...

  7. 利用HttpWebRequest访问WebApi

    WebApi现在越来越流行,下面给出利用HttpWebRequest访问WebApi的工具方法: 1.利用基准URL和参数字典生成完整URL /// <summary> /// 生成URL ...

  8. HttpWebRequest 基础连接已经关闭: 接收时发生错误

    HttpWebRequest request = null; Stream webStream = null; HttpWebResponse response = null; StreamReade ...

  9. C#中HttpWebRequest的GetRequestStream执行的效率太低,甚至偶尔死掉

    为了提高httpwebrequest的执行效率,查到了一些如下设置 request.ServicePoint.Expect100Continue = false; request.ServicePoi ...

随机推荐

  1. 3 Suggested Oracle Certifications For Oracle Form's Developers

    The following are the most suggested Oracle Certifications for Oracle Application Developers in Form ...

  2. Aspose.Total for .NET 2015 - Unlimited License z

    How to license Aspose.Total for .NET products Add "License.cs" [C#] OR "License.vb&qu ...

  3. python 浮点数保留小数

    http://www.cnblogs.com/Raymon-Geng/p/5784290.html 这里有三种方法, round(a,2) '%.2f' % a Decimal('5.000').qu ...

  4. DIY树莓派之随身工具箱

    摆弄树莓派有一年多了,在这里把经验分享给大家,少走弯路. 先放图两张. 搭建目的: wifi信号中转站\网站服务器\IC卡渗透测试\中间人\otr… 基于树莓派3 系统为Kali Linux 2017 ...

  5. 启动mongodb报错问题

    [root@zk-datanode-02 mongodb]# bin/mongod -f config/mongo.cnf &[1] 30549[root@zk-datanode-02 mon ...

  6. 【京东个人中心】——Nodejs/Ajax/HTML5/Mysql爬坑之静态页面

    一.引言 接着上一篇,京东个人中心的所有功能数据分析完成之后,现在需要把静态页面完成,实现过程中要用到的技术有:Bootstrap.html5表单新特性等.除此之外,还要利用Node.js的Expre ...

  7. Android 开发程序员必备网站

    开发必备网站: Android 开发各种工具下载 Android 开发国内大牛集合 Android 开发技术博客周刊 Android 开发技术周报中文版 Android 优秀开源项目集合以及源码分析 ...

  8. mapreduce_template

    Hadoop Tutorial - YDN https://developer.yahoo.com/hadoop/tutorial/module4.html import java.io.IOExce ...

  9. XML完成小程序

    XML文档的格式如下: <?xml version="1.0" encoding="utf-8"?> <学生名单> <学生 Nam ...

  10. jquery插件函数传参错误

    1.jquery传参通过json,可能的错误是,参数中的结束符写成了;