【发布时间】:2013-01-09 06:15:25
【问题描述】:
我有一个开放的SqlConnection 和这样的代码:
using (var transaction = connection.BeginTransaction()) {
using (var command = connection.CreateCommand()) {
command.Transaction = transaction;
command.CommandText = "MyQueryText";
using( var reader = command.ExecuteReader() ) {
//read data
}
}
}
I've been experiencing some "impossible code" symptoms 并订阅了SqlConnection.StateChange 事件,现在我发现在某些时候使用以下堆栈调用事件(状态从Open 更改为Closed):
at MyHandler.onStateChange(Object sender, StateChangeEventArgs e)
at System.Data.ProviderBase.DbConnectionInternal.CloseConnection(DbConnection owningObject, DbConnectionFactory connectionFactory)
at System.Data.SqlClient.SqlConnection.Close()
at System.Data.SqlClient.SqlInternalConnectionTds.BreakConnection()
at System.Data.SqlClient.TdsParserStateObject.ReadSniError(TdsParserStateObject stateObj, UInt32 error)
at System.Data.SqlClient.TdsParserStateObject.ReadSni(DbAsyncResult asyncResult, TdsParserStateObject stateObj)
at System.Data.SqlClient.TdsParserStateObject.ReadNetworkPacket()
at System.Data.SqlClient.TdsParserStateObject.ReadByte()
at System.Data.SqlClient.SqlDataReader.SetMetaData(_SqlMetaDataSet metaData, Boolean moreInfo)
at System.Data.SqlClient.TdsParser.Run(RunBehavior runBehavior, SqlCommand cmdHandler, SqlDataReader dataStream, BulkCopySimpleResultSet bulkCopyHandler, TdsParserStateObject stateObj)
at System.Data.SqlClient.SqlDataReader.ConsumeMetaData()
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)
at System.Data.SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, String method, DbAsyncResult result)
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.ExecuteReader()
// my code calling `ExecuteReader()`
所以运行时遇到一些随机错误(我猜是网络连接问题)并关闭连接,然后将关闭的阅读器对象返回给我的代码,我尝试使用返回的阅读器产量 InvalidOperationException。
我需要以某种方式解决它。显然会发生随机网络错误。我的代码中有重试逻辑,可以处理网络问题引发的SqlExceptions,但在这里我面对的是一个封闭的读者,然后是InvalidOperationException。
我的第一个想法是编写我自己的ExecuteReader(),它将调用本机ExecuteReader(),检查是否返回了封闭的阅读器,如果发生这种情况,则抛出一个新的ClosedReaderReturnedException,我还将更改重试代码,以便它也会对此类异常做出反应并重新运行查询。
我的解决方案好吗?有没有更好的解决方案?
【问题讨论】:
-
在连接网站上提交错误。如果你从你的活动中抛出会发生什么?您的异常会使其备份到执行阅读器吗?
-
@AbdElRaheim:我会提交一个错误,但修复它需要很长时间,或者他们甚至会“按设计”关闭它,我现在需要一个解决方法。这不能可靠地复制,所以我不能真正彻底地测试它。
-
调用executereader后是否可以检查连接状态?也许制作一个扩展方法,将在命令上调用执行阅读器,然后检查连接状态。也许还有一个 read() 方法可以做同样的检查
-
@AbdElRaheim:这或多或少是我的建议,不是吗?
-
哦。这是一个很好的解决方案:)
标签: c# .net sql-server-2005