c# - 超时已过。在操作完成之前超时期限已过,或者服务器没有响应。该语句已终止

标签 c# asp.net sql-server-2008-r2 timeout sqlcommand

我的网站上有很多用户(每天 20000-60000 人),这是一个移动文件下载网站。我可以远程访问我的服务器(windows server 2008-R2)。
我以前收到过“服务器不可用” 错误,但现在我看到了连接超时错误。
我对此不熟悉 - 为什么会发生,我该如何解决?

完整错误如下:

Server Error in '/' Application. Timeout expired. The timeout period elapsed prior to completion of the operation or the server is not responding. The statement has been terminated. Description: An unhandled exception occurred during the execution of the current web request. Please review the stack trace for more information about the error and where it originated in the code.

Exception Details: System.Data.SqlClient.SqlException: Timeout expired. The timeout period elapsed prior to completion of the operation or the server is not responding. The statement has been terminated.

Source Error:

An unhandled exception was generated during the execution of the current web request. Information regarding the origin and location of the exception can be identified using the exception stack trace below.

Stack Trace:

[SqlException (0x80131904): Timeout expired. The timeout period elapsed prior to completion of the operation or the server is not responding. The statement has been terminated.]
System.Data.SqlClient.SqlConnection.OnError(SqlException exception, Boolean breakConnection) +404
System.Data.SqlClient.TdsParser.ThrowExceptionAndWarning() +412
System.Data.SqlClient.TdsParser.Run(RunBehavior runBehavior, SqlCommand cmdHandler, SqlDataReader dataStream, BulkCopySimpleResultSet bulkCopyHandler, TdsParserStateObject stateObj) +1363
System.Data.SqlClient.SqlCommand.FinishExecuteReader(SqlDataReader ds, RunBehavior runBehavior, String resetOptionsString) +6387741
System.Data.SqlClient.SqlCommand.RunExecuteReaderTds(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, Boolean async) +6389442
System.Data.SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, String method, DbAsyncResult result) +538
System.Data.SqlClient.SqlCommand.InternalExecuteNonQuery(DbAsyncResult result, String methodName, Boolean sendToPipe) +689
System.Data.SqlClient.SqlCommand.ExecuteNonQuery() +327
NovinMedia.Data.DbObject.RunProcedure(String storedProcName, IDataParameter[] parameters, Int32& rowsAffected) +209
DataLayer.OnlineUsers.Update_SessionEnd_And_Online(Object Session_End, Boolean Online) +440
NiceFileExplorer.Global.Application_Start(Object sender, EventArgs e) +163

[HttpException (0x80004005): Timeout expired. The timeout period elapsed prior to completion of the operation or the server is not responding. The statement has been terminated.]
System.Web.HttpApplicationFactory.EnsureAppStartCalledForIntegratedMode(HttpContext context, HttpApplication app) +4052053
System.Web.HttpApplication.RegisterEventSubscriptionsWithIIS(IntPtr appContext, HttpContext context, MethodInfo[] handlers) +191
System.Web.HttpApplication.InitSpecial(HttpApplicationState state, MethodInfo[] handlers, IntPtr appContext, HttpContext context) +352
System.Web.HttpApplicationFactory.GetSpecialApplicationInstance(IntPtr appContext, HttpContext context) +407
System.Web.Hosting.PipelineRuntime.InitializeApplication(IntPtr appContext) +375

[HttpException (0x80004005): Timeout expired. The timeout period elapsed prior to completion of the operation or the server is not responding. The statement has been terminated.]
System.Web.HttpRuntime.FirstRequestInit(HttpContext context) +11686928 System.Web.HttpRuntime.EnsureFirstRequestInit(HttpContext context) +141 System.Web.HttpRuntime.ProcessRequestNotificationPrivate(IIS7WorkerRequest wr, HttpContext context) +4863749


回答后编辑:
我在 Global.asax 中的 Application_Start 如下所示:

protected void Application_Start(object sender, EventArgs e)
{
    Application["OnlineUsers"] = 0;

    OnlineUsers.Update_SessionEnd_And_Online(
        DateTime.Now,
        false);

    AddTask("DoStuff", 10);
}

被调用的存储过程是:

ALTER Procedure [dbo].[sp_OnlineUsers_Update_SessionEnd_And_Online]
    @Session_End datetime,
    @Online bit
As
Begin
    Update OnlineUsers
    SET
        [Session_End] = @Session_End,
        [Online] = @Online

End

我有两种获取在线用户的方法:

  1. 使用 Application["OnlineUsers"] = 0;
  2. 另一个使用数据库

因此,对于方法 #2,我在 Application_Start 重置了所有 OnlineUser。该表中有超过 482,751 条记录。

最佳答案

看起来您的查询花费的时间超过了应有的时间。 从您的堆栈跟踪和您的代码中,您应该能够准确地确定那是什么查询。

这种类型的超时可能有三种原因;

  1. 某个地方出现了死锁
  2. 数据库的统计信息和/或查询计划缓存不正确
  3. 查询太复杂,需要调优

死锁可能很难修复,但很容易确定是否是这种情况。使用 Sql Server Management Studio 连接到您的数据库。在左 Pane 中右键单击服务器节点并选择事件监视器。查看正在运行的进程。 通常大多数将处于空闲或运行状态。出现问题时,您可以通过进程状态识别任何阻塞的进程。如果您右键单击该进程并选择详细信息,它将向您显示该进程执行的最后一个查询。

第二个问题会导致数据库使用次优的查询计划。可以通过清除统计信息来解决:

exec sp_updatestats

如果不行你也可以试试

dbcc freeproccache

当你的服务器负载很重时,你不应该这样做,因为它会暂时导致很大的性能损失,因为所有存储过程和查询在第一次执行时都会重新编译。 但是,由于您声明问题有时 发生,并且堆栈跟踪表明您的应用程序正在启动,我认为您运行的查询只是偶尔运行。强制 SQL Server 不重用以前的查询计划可能会更好。参见 this answer有关如何执行此操作的详细信息。

我已经谈到了第三个问题,但是您可以通过手动执行查询(例如使用 Sql Server Management Studio)轻松确定查询是否需要调整。如果查询需要很长时间才能完成,即使在重置统计信息之后,您也可能需要对其进行调整。如需这方面的帮助,您应该在新问题中发布确切的查询。

关于c# - 超时已过。在操作完成之前超时期限已过,或者服务器没有响应。该语句已终止,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8602395/

相关文章:

C# - 简单验证 - DialogResult

c# - 按 len() 排序,但在 C# 的 linq 中

asp.net - 用户登录网站时的 T-SQL AES 加密与哈希/加盐

sql-server - SQL_ATTR_QUERY_TIMEOUT 未超时

c# - 合并两个数据表

c# - Windows Phone 8.1 的绘图控件(通用应用程序)

c# - 在 MVC4 中使用 @Html.RenderAction 不显示页面

sql-server - 使用 ORDER BY 子句创建 View

reporting-services - 我可以使用 SQL Server 2008 R2 在 VS 2015 中创建 SSRS 报告吗?

c# - 从 .NET DLL 文件生成 PDB?