C# 从代码而不是查询工具运行存储过程时超时

C# 从代码而不是查询工具运行存储过程时超时,c#,sql-server,stored-procedures,C#,Sql Server,Stored Procedures,我试图弄清楚为什么在SQLServerExpress查询窗口中调用存储过程需要几秒钟,但当我在代码中运行调用存储过程时,查询超时。我们正在使用SQLServer2008。我知道在没有看到存储过程的情况下很难准确地说出发生了什么。我只是希望这是一个已知的问题。非常感谢您的指导 在SQL server express查询窗口中调用“存储过程”并在2秒内运行的SQL查询: EXEC STORED_PROCEDURE_X '07/01/2010', '07/31/2010', 0, '', 'true'

我试图弄清楚为什么在SQLServerExpress查询窗口中调用存储过程需要几秒钟,但当我在代码中运行调用存储过程时,查询超时。我们正在使用SQLServer2008。我知道在没有看到存储过程的情况下很难准确地说出发生了什么。我只是希望这是一个已知的问题。非常感谢您的指导

在SQL server express查询窗口中调用“存储过程”并在2秒内运行的SQL查询:

EXEC STORED_PROCEDURE_X '07/01/2010', '07/31/2010', 0, '', 'true','', 'Top 20'
调用“存储过程”并超时的代码:

SqlConnection connSQL = null;
SqlCommand sqlCmd = null;
SqlDataAdapter sqlDataAdpater = null;
DataTable returnData = null;

try
{
    returnData = new DataTable();
    connSQL = new SqlConnection(sqlConnection);
    sqlCmd = new SqlCommand("STORED_PROC_X", connSQL);
    if (connSQL.State == ConnectionState.Closed)
    {
        connSQL.Open();
    }
    sqlCmd.CommandType = CommandType.StoredProcedure;
    sqlCmd.CommandTimeout = 600;
    sqlCmd.Parameters.Add("@StartDate", SqlDbType.NVarChar).Value = "07/01/2010";
    sqlCmd.Parameters.Add("@EndDate", SqlDbType.NVarChar).Value = "07/31/2010";

    sqlCmd.Parameters.Add("@AuditType", SqlDbType.Int).Value = "0";

    sqlCmd.Parameters.Add("@SortBy", SqlDbType.NVarChar).Value = "";

    sqlCmd.Parameters.Add("@IsClaimDepartment", SqlDbType.NVarChar).Value = "true";
    sqlCmd.Parameters.Add("@IdsList", SqlDbType.NVarChar).Value = "";
    sqlCmd.Parameters.Add("@ReportType", SqlDbType.NVarChar).Value = "Top 20";
    sqlDataAdpater = new SqlDataAdapter(sqlCmd);
    sqlDataAdpater.Fill(returnData);
    if (connSQL.State == ConnectionState.Open)
    {
        connSQL.Close();
    }
    return returnData;
}
catch (Exception ex)
{
    LogErrorMessages("ExecuteStoredProcedure", ex.Message);
    throw ex;
}
收到异常:

System.Data.SqlClient.SqlException: Timeout expired.  The timeout period elapsed prior to completion of the operation or the server is not responding.

您是否在存储过程中使用任何事务?未提交的事务将导致此错误消息。

尝试a)重新组织代码,b)增加超时:

DataTable returnData = null;

try
{
    using(SqlConnection connSQL = new SqlConnection(sqlConnection))
    using(SqlCommand sqlCmd = new SqlCommand("STORED_PROC_X", connSQL))
    {
       sqlCmd.CommandType = CommandType.StoredProcedure;
       sqlCmd.CommandTimeout = 1200;

       // those two parameters should really be SqlDbType.DateTime!!
       sqlCmd.Parameters.Add("@StartDate", SqlDbType.NVarChar, 25).Value = "07/01/2010";
       sqlCmd.Parameters.Add("@EndDate", SqlDbType.NVarChar, 25).Value = "07/31/2010";

       sqlCmd.Parameters.Add("@AuditType", SqlDbType.Int).Value = "0";

       sqlCmd.Parameters.Add("@SortBy", SqlDbType.NVarChar, 50).Value = "";

       // this parameter should really be SqlDbType.Bit !!
       sqlCmd.Parameters.Add("@IsClaimDepartment", SqlDbType.NVarChar, 50).Value = "true";

       sqlCmd.Parameters.Add("@IdsList", SqlDbType.NVarChar, 25).Value = "";
       sqlCmd.Parameters.Add("@ReportType", SqlDbType.NVarChar, 25).Value = "Top 20";

       SqlDataAdapter sqlDataAdpater = new SqlDataAdapter(sqlCmd);

       returnData = new DataTable();
       sqlDataAdpater.Fill(returnData);
   }

   return returnData;
}
catch (Exception ex)
{
   LogErrorMessages("ExecuteStoredProcedure", ex.Message);
   throw;
}
SqlDataAdapter
将打开和关闭连接本身-无需显式执行此操作

此外,我会

  • 为NVARCHAR参数定义一个合理的最大长度(存储的过程除了什么)
  • 将日期作为日期时间传递!(不是NVARCHAR)
  • 将布尔值作为位传递!(不是NVARCHAR)
  • 重新抛出异常时,只使用
    throw
    ,而不使用
    throw ex
    (如果使用
    throw ex
    ,基本上就是破坏堆栈跟踪,无法找出异常真正来自何处)

假设您从代码中传递的参数与在SSMS中测试时相同,并且您的SSMS测试在数据类型使用方面完全相同,我会认为这可能是一个参数嗅探问题


您是否有权访问SQL Profiler(不随Express edition提供)以获取两个实际执行计划?如果没有,您可以按照建议获取计划。

我遇到了一个类似的问题,即存储过程的运行速度比查询窗口中的同一查询慢。 我尝试了从参数嗅探编码(局部变量)、删除聚集索引到仅使用非聚集索引等所有方法。使用nvarchar参数检索varchar字段仍然需要22秒分钟

我最初认为这只是nvarchar和varchar之间的区别,并将数据库字段更改为nvarchar。我又浪费了整整一天的时间,将5000万条记录移动到一个新表并重新编制索引。还是用了22秒

最后,我将表中的任何键字段从nvarchar更改为varchar,以及所有参数和wow;返回道恩不到1秒

我坚信这是SQL Server中的一个错误,从未得到纠正。如何在查询窗口中直接运行查询,或从vb.net或c#代码调用sql并在不到1秒的时间内获得结果;然后在存储过程中使用参数运行相同的查询,并得到如此可怕的结果

简短回答:不惜一切代价远离nvarchar数据类型

另外,学习使用merge语句将数据移动到大型表中以避免超时。 运行大型合并查询时,将恢复模式设置为simple;然后恢复到完全恢复状态

孩子,这周我学到了很多。超过80小时的教育,我不需要。
但是,LinkToMeet.com现在拥有超过1.5亿的成员,而且一切正常。

确保传递给SP的参数与数据库上的参数匹配[区分大小写]

因此,在管理控制台中运行一个返回30条记录的存储过程花费了我00:00秒,但在.net中加载它大约需要40秒,超过默认的30秒超时


我只需修改存储过程并重新运行
ALTER过程
。。。代码不做任何更改,问题立即得到解决。关于这个错误的来源,我没有更多的细节,但至少它是一个非常快速的修复方法,帮助我一直很大的是在过程中添加“with recompile”选项


更改命令超时=0

sqlCmd.CommandTimeout = 0;

我也有同样的问题。我的存储过程是从MSSMS或dbForgeStudio执行的,但不是从C#代码(SqlCommand)执行的。我通过更改SQL server中的存储过程(无任何更改)修复了此问题

我尝试过使用“with recompile”和“arithabort off”来更改代码等,但最后只有重新启动sql server我才解决了问题。

我们也遇到了同样的问题,并认为这是参数嗅探,但在尝试了许多事情之后,包括更改参数嗅探、使用with recompile、删除/重新创建、更新统计信息,释放进程缓存时,我们发现这些都不起作用。我们追踪到一个需要添加的索引。我们刚刚从传统的基数估计量转换为2014年后的估计量。切换到旧的估计器解决了这个问题,或者使用新的估计器并添加索引。

我不知道这是否有帮助,但我会在打开连接之前完全构建命令。@AllenG:另外,我会使用(…){……}/code>块将
SqlConnection
SqlCommand
放入
,我注意到一点:当您从SSMS执行时,您并没有提供Unicode字符串-从您的代码中,您是。存储过程需要什么??瓦查尔还是瓦查尔??另外:为什么不在代码中为NVARCHAR参数指定maxa长度?是的,从NVARCHAR进行的这些类型转换也可能会导致使用索引时出现问题。更改过程也节省了我的时间。。。。。想知道为什么吗?有专家的意见吗?似乎编译的存储过程在某种程度上被破坏了。您究竟是如何得出结论,这是一个比这里已经建议的更好的解决方案的?先生,在我们的代码中,我们可以将命令超时设置为0,以便在存储过程完成之前代码不会给出错误。先生。这对我来说确实有效。我必须尝试一下,我急切地想找到一个快速的解决办法。但是我需要弄清楚为什么SP执行起来很慢