2013-05-14 114 views
0

我有一個存儲過程,它可以完成很多連接。查詢雖然運行得非常快,大約3秒鐘。我只是不知道下面的錯誤每隔一段時間就會彈出。我的事件緩存使用此查詢一分鐘的文檔,所以它不會一遍又一遍地運行。我正在使用實體框架5,並且我的存儲過程正在使用CTE來進行分頁。任何線索或見解?SQL Server Express 2008,連接和超時過期錯誤消息

System.Data.SqlClient.SqlException (0x80131904): Timeout expired. The timeout period elapsed prior to completion of the operation or the server is not responding. ---> System.ComponentModel.Win32Exception (0x80004005): The wait operation timed out 
    at System.Data.SqlClient.SqlConnection.OnError(SqlException exception, Boolean breakConnection, Action`1 wrapCloseInAction) 
    at System.Data.SqlClient.SqlInternalConnection.OnError(SqlException exception, Boolean breakConnection, Action`1 wrapCloseInAction) 
    at System.Data.SqlClient.TdsParser.ThrowExceptionAndWarning(TdsParserStateObject stateObj, Boolean callerHasConnectionLock, Boolean asyncClose) 
    at System.Data.SqlClient.TdsParser.TryRun(RunBehavior runBehavior, SqlCommand cmdHandler, SqlDataReader dataStream, BulkCopySimpleResultSet bulkCopyHandler, TdsParserStateObject stateObj, Boolean& dataReady) 
    at System.Data.SqlClient.SqlDataReader.TryConsumeMetaData() 
    at System.Data.SqlClient.SqlDataReader.get_MetaData() 
    at System.Data.SqlClient.SqlCommand.FinishExecuteReader(SqlDataReader ds, RunBehavior runBehavior, String resetOptionsString) 
    at System.Data.SqlClient.SqlCommand.RunExecuteReaderTds(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, Boolean async, Int32 timeout, Task& task, Boolean asyncWrite) 
    at System.Data.SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, String method, TaskCompletionSource`1 completion, Int32 timeout, Task& task, Boolean asyncWrite) 
    at System.Data.SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, String method) 
    at System.Data.SqlClient.SqlCommand.ExecuteReader(CommandBehavior behavior, String method) 
    at System.Data.SqlClient.SqlCommand.ExecuteDbDataReader(CommandBehavior behavior) 
    at System.Data.Common.DbCommand.ExecuteReader() 
    at System.Data.Objects.ObjectContext.ExecuteStoreQueryInternal[TElement](String commandText, String entitySetName, MergeOption mergeOption, Object[] parameters) 
    at System.Data.Objects.ObjectContext.ExecuteStoreQuery[TElement](String commandText, Object[] parameters) 
    at System.Data.Entity.Internal.InternalContext.ExecuteSqlQuery[TElement](String sql, Object[] parameters) 
    at System.Data.Entity.Internal.InternalContext.ExecuteSqlQueryAsIEnumerable[TElement](String sql, Object[] parameters) 
    at System.Data.Entity.Internal.InternalContext.ExecuteSqlQuery(Type elementType, String sql, Object[] parameters) 
    at System.Data.Entity.Internal.InternalSqlNonSetQuery.GetEnumerator() 
    at System.Data.Entity.Internal.InternalSqlQuery`1.GetEnumerator() 
    at System.Collections.Generic.List`1..ctor(IEnumerable`1 collection) 
    at System.Linq.Enumerable.ToList[TSource](IEnumerable`1 source) 
    at Tournaments.Data.Repositories.Games.GamesRepository.GetGamesPaged(IGamesCriteria criteria) 

實體框架方法

public PagedResult<GameComplex> GetGamesPaged(IGamesCriteria criteria) 
     { 
      var results = DataContext.Database.SqlQuery<GameComplex>("EXEC [Schema].[Database] @Page, @PageSize, @SortOrder, @SortDirection, @EventId, @DivisionId, @DivisionTeamId, @Date, @SearchToken, @MemberId", 
       new SqlParameter("Page", criteria.Page), 
       new SqlParameter("PageSize", criteria.PageSize), 
       new SqlParameter("SortOrder", GetDataValue(criteria.SortOrder)), 
       new SqlParameter("SortDirection", GetDataValue(criteria.SortDirection)), 
       new SqlParameter("EventId", GetDataValue(criteria.EventId)), 
       new SqlParameter("DivisionTeamId", GetDataValue(criteria.DivisionTeamId)), 
       new SqlParameter("DivisionId", GetDataValue(criteria.DivisionId)), 
       new SqlParameter("Date", GetDataValue(criteria.Date)), 
       new SqlParameter("SearchToken", GetDataValue(criteria.SearchToken)), 
       new SqlParameter("MemberId", GetDataValue(criteria.MemberId))).ToList(); 

      return new PagedResult<GameComplex> 
         { 
          Page = criteria.Page, 
          PageSize = criteria.PageSize, 
          Total = results.Any(q => q != null) ? results.FirstOrDefault().Total : 0, 
          Results = results 
         }; 
     } 

SQL Server存儲過程的參數簽名

ALTER PROCEDURE [Schema].[Database] 
    @Page INT = 1, 
    @PageSize INT = 10, 
    @SortOrder NVARCHAR(100) = 'Id', 
    @SortDirection VARCHAR(4) = 'ASC', 
    @EventId INT = NULL, 
    @DivisionId INT = NULL, 
    @DivisionTeamId INT = NULL, 
    @Date DATETIME = NULL, 
    @SearchToken NVARCHAR(100) = NULL, 
    @MemberId INT = NULL 
AS 

回答

3

您可能需要調整命令超時。

參見:

Set Command Timeout in entity framework 4.3

How to set CommandTimeout for DbContext?

編輯

命令超時:

http://msdn.microsoft.com/en-us/library/system.data.sqlclient.sqlcommand.commandtimeout.aspx

連接超時:

http://msdn.microsoft.com/en-us/library/system.data.sqlclient.sqlconnection.connectiontimeout.aspx

編輯:

另一個可能的問題是 「參數嗅探」。

http://blogs.msdn.com/b/queryoptteam/archive/2006/03/31/565991.aspx

所以嘗試參數嗅探解決方法之一:

ALTER PROCEDURE [Schema].[Database] 
    @Page INT = 1, 
    @PageSize INT = 10, 
    @SortOrder NVARCHAR(100) = 'Id', 
    @SortDirection VARCHAR(4) = 'ASC', 
    @EventId INT = NULL, 
    @DivisionId INT = NULL, 
    @DivisionTeamId INT = NULL, 
    @Date DATETIME = NULL, 
    @SearchToken NVARCHAR(100) = NULL, 
    @MemberId INT = NULL 
AS 

Declare @PageCopyOf int 
Select @PageCopyOf = @Page 


Declare @PageSizeCopyOf int 
Select @PageSizeCopyOf = @PageSize 

Declare @SortOrderCopyOf NVARCHAR(100) 
Select @SortOrderCopyOf = @SortOrder 

Declare @SortDirectionCopyOf VARCHAR(4) 
Select @SortDirectionCopyOf = @SortDirection 

Declare @EventIdCopyOf int 
Select @EventIdCopyOf = @EventId 

Declare @DivisionIdCopyOf int 
Select @DivisionIdCopyOf = @DivisionId 


Declare @DivisionTeamIdCopyOf int 
Select @DivisionTeamIdCopyOf = @DivisionTeamId 

Declare @DateCopyOf DATETIME 
Select @DateCopyOf = @Date 

Declare @SearchTokenCopyOf NVARCHAR(100) 
Select @SearchTokenCopyOf = @SearchToken 

Declare @MemberIdCopyOf int 
Select @MemberIdCopyOf = @MemberId 

然後一切都低於這個使用/消耗@XXXXXCopyOf變量,而不是原始變量(名稱)。

這是值得一試。

+0

命令超時對存儲過程是否以相同的方式工作?看看上面的代碼。 –

+0

在ADO.NET術語中.... SqlCommand.Timeout到底需要多長時間才能運行存儲過程,然後纔會超時並「放棄」。 – granadaCoder

+0

好吧,我找到了命令對象並更新它。如果這能起作用,那麼應該標記你的答案,因爲它更有意義。 –

1

只是一個猜測,但查詢跑得快(3秒),只有當它被緩存。否則,它會花費更長的時間並且超過您的服務器超時設置。由於System.Data.SqlClient引發異常,因此默認的超時時間很可能只有15秒。

MSDN: "The default value is 15 seconds"

或者,SqlCommand對象,默認的CommandTimeout屬性嘗試爲30秒。

CommandTimeout

+0

我有180秒的連接字符串,你認爲那不是正確的地方?

+0

嘗試使用ConnectTimeout,而不需要在單詞之間進行匹配。從同一頁面:」您可以使用ConnectTimeout或Connection Timeout關鍵字設置連接等待超時的時間量「 – ExactaBox

+0

我只看到帶空格的示例,但我用「連接」而不是「連接」去了,看看是否解決了這個問題,如果是這樣的話,將其標記爲正確。 –