我最近將項目從EF5升級到了EF6。在這個項目中,我有一個定期運行的Azure工作者角色,並啓動SQL Azure上的一個存儲過程,該過程更新一堆數據庫信息,平均需要1.5小時執行。完成後,輔助角色將使用存儲過程的返回結果執行其他任務。執行長時間運行的存儲過程的EF6會出現超時錯誤
這用來在EF5工作得很好,但在EF6它每一次失敗,這些錯誤之一:
Error A transport-level error has occurred when receiving results from the server. (provider: Session Provider, error: 19 - Physical connection is not usable)
Error The session has been terminated because it has acquired too many locks. Try reading or modifying fewer rows in a single transaction. A severe error occurred on the current command. The results, if any, should be discarded.
我曾嘗試下面的東西來修復錯誤:
- 驗證所有存儲過程讀取都有
WITH (NOLOCK)
修飾符 - 將實體框架上下文的超時增加到5小時
- 刪除了落實到位,並把它回落到使用
DefaultExecutionStrategy
- 移除了在存儲過程中發生的任何交易
- 確保這一步的工作者角色在它自己的上下文中運行新
SqlAzureExecutionStrategy
實施例:
using (var dbContext = new EFEntityContext())
{
// set the timeout to 5 hours
var objectContext = (dbContext as IObjectContextAdapter).ObjectContext;
objectContext.CommandTimeout = 18000; // 5 hours
// update all active curriculums
var result = dbContext.usp_MyLongRunningProd();
// log the results of the operation
Trace.TraceInformation(result);
}
而且,存儲的過程中讀取一個大表成光標,通過它循環,並執行基於各項目進行分析,數據的變化。我不需要遊標處於任何類型的事務中,也不需要使用我所知道的遊標,除非EF正在創建一個,那就是問題所在。