我们刚刚注意到executionTimeout已停止在我们的网站上运行。去年它肯定在工作......很难说什么时候停止了。
我们目前正在运行:
Web.Config
<compilation defaultLanguage="vb" debug="false" batch="true">
<httpRuntime executionTimeout="90" />
为什么我们看到Timetaken一直到约20分钟的任何暗示。 DebugType(完全vs pdbonly)的编译选项会有任何影响吗?
datetime timetaken httpmethod Status Sent Received<BR>
12/19/10 0:10 901338 POST 302 456 24273<BR>
12/19/10 0:18 1817446 POST 302 0 114236<BR>
12/19/10 0:16 246923 POST 400 0 28512<BR>
12/19/10 0:12 220450 POST 302 0 65227<BR>
12/19/10 0:22 400150 GET 200 180835 416<BR>
12/19/10 0:20 335455 POST 400 0 36135<BR>
12/19/10 0:57 213210 POST 302 0 51558<BR>
12/19/10 0:48 352742 POST 302 438 25802<BR>
12/19/10 0:37 958660 POST 400 0 24558<BR>
12/19/10 0:06 202025 POST 302 0 58349<BR>
答案 0 :(得分:7)
执行超时和耗时两个不同的事情。虽然,这种差异的大小令人不安。
所花费的时间包括请求/响应中的所有网络时间(在某些conditions下)。网络传输时间很容易超过请求真正需要的时间。虽然,通常情况下,我习惯了几分钟而不是几分钟。
执行超时仅指工作进程处理请求所花费的时间;这只是时间的一部分。它仅适用于debug attribute is set to false;它看起来像你。
当然,假设您列出的第一个请求花了整整90秒的允许超时时间,那么在时间窗口中还剩下13.5分钟来传输基本上24k的数据。这听起来像是一个严重的网络问题。
因此,要么您有严重的传输问题,要么正在处理请求的树中的某个地方存在另一个web.config文件,该文件将debug设置为true或将执行超时增加到天文数字。
另一种可能性是页面本身具有debug属性集或者它自己的超时值。
答案 1 :(得分:0)
我有一个理论,但我不确定如何证明它。我做了类似cbcolin的事情,并记录了BeginRequest
事件处理程序中请求开始的时间。然后,当请求超时(在我们的情况下为1小时后),它将记录在数据库中并记录时间戳。
所以这就是理论:ASP.NET只计算线程实际执行的时间,而不是它睡着的时间。
所以在BeginRequest
之后,线程进入睡眠状态,直到IIS收到整个POST主体。然后线程被唤醒以便工作并且executionTimeout
时钟开始运行。因此,在网络传输阶段花费的时间不计入executionTimeout
。最终,站点范围的连接超时被命中,IIS关闭连接,导致ASP.NET中出现异常。
BeginRequest
甚至PreRequestHandlerExecute
在POST主体转移到Web服务器之前都被称为 。然后在调用请求处理程序之前有一个很长的间隙。所以看起来.NET可能有30分钟的请求,但线程运行时间不长。
我将开始记录请求处理程序实际开始运行的时间,并查看它是否超过了我设置的限制。
现在,为了控制请求在每个URL的基础上保持传输阶段的时间,我不知道。在全局级别,我们可以在webLimits中为应用程序设置minBytesPerSecond。我找不到它的用户界面。这应该会在传输阶段激起超慢客户端。
这仍然无法解决实际发送数据的DoS攻击的问题。
答案 2 :(得分:0)
2天前,当我遇到同样的问题时,我发现了这篇文章。我尝试了一切,它在我的本地机器上运行但在生产服务器上不起作用。今天,我有一个解决方法,解决问题,并希望分享。微软似乎没有对IHttpAsyncHandler应用超时,我利用了这一点。在我的系统上,我只有一个耗时的处理程序,所以这个解决方案适合我。 我的处理程序代码如下所示:
public class Handler1 : IHttpAsyncHandler
{
public bool IsReusable
{
get { return true; }
}
public void ProcessRequest(HttpContext context)
{
}
public IAsyncResult BeginProcessRequest(HttpContext context, AsyncCallback cb, object extraData)
{
//My business logic is here
AsynchOperation asynch = new AsynchOperation(cb, context, extraData);
asynch.StartAsyncWork();
return asynch;
}
public void EndProcessRequest(IAsyncResult result)
{
}
}
我的助手班:
class AsynchOperation : IAsyncResult
{
private bool _completed;
private Object _state;
private AsyncCallback _callback;
private HttpContext _context;
bool IAsyncResult.IsCompleted { get { return _completed; } }
WaitHandle IAsyncResult.AsyncWaitHandle { get { return null; } }
Object IAsyncResult.AsyncState { get { return _state; } }
bool IAsyncResult.CompletedSynchronously { get { return false; } }
public AsynchOperation(AsyncCallback callback, HttpContext context, Object state)
{
_callback = callback;
_context = context;
_state = state;
_completed = false;
}
public void StartAsyncWork()
{
_completed = true;
_callback(this);
}
}
在这种方法中,我们实际上不会异步做任何事情。 AsynchOperation
只是一个假的asyn任务。我的所有业务逻辑仍然在主线程上执行,这不会改变当前代码的任何行为。