我在不同的类中有几部分代码使用这个或非常相似的代码从SQL Server数据库中提取一些数据。他们中的大多数都有效,但是我遇到了一些问题但实际上并不明白为什么。上面的代码将执行60-64次,检索行但随后它会因无效读取错误而爆炸。香港专业教育学院追踪记录的任何事情,但它似乎只是打在那些记录和停止之间的任何地方。从这个类到任何其他类函数都没有调用,基本上,这是运行的onyl事件。
我的连接字符串有超过600秒的时间,我也设置了火星。另一个说明;这是从Parallel.ForEach调用并行性设置为2。
正如我所说,我在整个程序中使用这种代码结构,大多数工作都很好,让我担心的不仅仅是错误,而是它的出现不一致。
当我摆脱Parallel.ForEach并将其作为foreach运行时,它可以工作。我需要那些线程,否则这需要太长时间。而且我也很好奇读者正在关闭的地方。
异常:System.InvalidOperationException - 读取器关闭时无效尝试调用Read。
被叫代码:
public string GetUnderwritingType(string id)
{
UnderwritingType uwt = new UnderwritingType();
GetRequiredPercent(id, ref uwt);
GetParticipation(id, ref uwt);
return CalculateUnderwritingType(ref uwt);
}
private void GetRequiredPercent(string id, ref UnderwritingType uwt)
{
DataCommon common = new DataCommon(Settings.Default.ReqPercentSP, id);
try
{
/******* Error on this reader statement ********/
using (SqlDataReader reader = common.Command.ExecuteReader(CommandBehavior.CloseConnection)) {
/* no data */
if (reader.HasRows == false) return;
while (reader.Read())
{
uwt.RequiredPercent.Add(Double.Parse(reader[REQ_PERCENT_FIELD].ToString()));
uwt.MinimumCount.Add(Int32.Parse(reader[MIN_COUNT_FIELD].ToString()));
uwt.UWType.Add(Int32.Parse(reader[UW_LEVEL_FIELD].ToString()));
}
}
}
catch (InvalidOperationException)
{
if (common.Connection.State == ConnectionState.Open) common.Connection.Close();
throw;
}
catch (SqlException)
{
if (common.Connection.State == ConnectionState.Open) common.Connection.Close();
throw;
}
}
设置连接的代码:
public class DataCommon
{
private readonly SqlCommand _command;
private SqlConnection _connection;
public DataCommon(string storedProcedure, string id)
{
SetConnection();
_command = new SqlCommand(storedProcedure, Connection);
if (_command != null) _command.CommandType = CommandType.StoredProcedure;
_command.Parameters.Add("@Id", SqlDbType.NVarChar).Value = id;
}
/// <summary>
/// Gets the database connection.
/// </summary>
public SqlConnection Connection
{
get { return _connection; }
}
/// <summary>
/// Gets the database command object.
/// </summary>
public SqlCommand Command
{
get { return _command; }
}
/// <summary>
/// Sets the database connection.
/// </summary>
private void SetConnection()
{
_connection = new SqlConnection {ConnectionString = Settings.Default.TestConnection};
_connection.Open();
if (_connection.State != ConnectionState.Open)
throw new DataException(Settings.Default.ConnectionErrorMessage);
}
}
连接字符串:数据源= xxxxx;初始目录= yyyyy; Trusted_Connection = True; MultipleActiveResultSets = True;连接超时= 600;
堆栈跟踪: .Data.SqlClient.SqlDataReader.ReadInternal(Boolean setTimeout) 在System.Data.SqlClient.SqlDataReader.Read() at GroupDataAccess.EligibilityClassData.GetEligibilityClass(String id)in C:\ Subversion \ branches \ Fimmas \ FimmasToInfoHub \ GroupHubFeed \ GroupData \ EligibilityClassData.cs:line 95 在C:\ Subversion \ branches \ Fimmas \ FimmasToInfoHub \ GroupHubFeed \ GroupLogic \ GroupExtract.cs中的GroupLogic.GroupExtract.BuildEligibilityClass(String id,Group&amp; group):第188行 在GroupLogic.GroupExtract。&lt;&gt; c_ DisplayClass2.b _1()在C:\ Subversion \ branches \ Fimmas \ FimmasToInfoHub \ GroupHubFeed \ GroupLogic \ GroupExtract.cs:第113行 在System.Threading.Tasks.Task.InnerInvoke() 在System.Threading.Tasks.Task.Execute()
初始调用循环(转换为普通foreach时,一切都很好):
ParallelOptions options = new ParallelOptions();
options.MaxDegreeOfParallelism = 2;
Parallel.ForEach(ids, options, id => BuildGroup(id));
来电
private void BuildGroup(string id)
{
Group[] group = { new Group() };
Task eligibilityBlock = Task.Factory.StartNew(() =>
BuildEligibilityClass(id, ref @group[0]));
Task.WaitAny(eligibilityBlock);
GroupList.Add(@group[0]);
}
哪个电话
private static void BuildEligibilityClass(string id, ref Group group)
{
EligibilityClassData eligClassData = new EligibilityClassData();
group.EligibilityClassList = eligClassData.GetEligibilityClass(id);
}
进入其中一个读数。
答案 0 :(得分:0)
您可以在以下两个位置增加超时值并尝试吗?
参考:
答案 1 :(得分:-1)
我对此有昵称......“CommandBehavior.CloseConnection”将在完成的第一个线程上关闭你的连接(这解释了不一致性)。 尝试删除此并删除关闭“catch”中的连接(仅用于测试)。