我对事务范围和隔离级别有一点疑问......所以我现在知道范围内的所有内容可能会也可能不会出现在根范围内,(拥有一个)这个条件取决于某些条件。
方案
我有一张表A,我想阻止它直到整个transcope提交。我不希望任何其他转发更新,删除或插入,因此此交易将被隔离为可序列化,并且表B将插入一些关键值A但是这个(b)不需要被阻止因为有些用户正在查询提交的数据甚至是脏数据**因此我已经理解了这个需求,所以这将是默认的隔离读取未提交。这是一种轻量级的事务
这是我的代码:
public bool nestedTranComplete(SomeModel thatModel) {
int secName = 0;
List<int> IDsList = new List<int>();
var opts = new TransactionOptions
{
IsolationLevel = System.Transactions.IsolationLevel.Serializable,
Timeout = new TimeSpan(0, 0, 9000)
};
var opts2 = new TransactionOptions
{
IsolationLevel = System.Transactions.IsolationLevel.ReadUncommitted,
Timeout = new TimeSpan(0, 1, 0)
};
try
{
using (TransactionScope scope = new TransactionScope(TransactionScopeOption.RequiresNew, opts))
{
using (SqlConnection con = new SqlConnection(SqlconnectionString))
{
using (SqlCommand cmdConsecutiveID = new SqlCommand("usp_GetNewSeqVal", con))
{
cmdConsecutiveID.CommandType = CommandType.StoredProcedure;
cmdConsecutiveID.Parameters.Add(new SqlParameter { SqlDbType = SqlDbType.VarChar,
ParameterName = "SeqName" }).Value = "Someprocess";
using (SqlDataReader readr = cmdConsecutiveID.ExecuteReader(CommandBehavior.SingleRow))
{
readr.Read();
secName = readr.GetInt32(0);
}
if (secName == 0)
{
throw new ArgumentException("no success on getting the new number", "SeqName");
}
}
}
using (TransactionScope DependingBlockingScope = new TransactionScope(TransactionScopeOption.Required, opts2))
{
using (SqlConnection con2 = new SqlConnection(SqlconnectionString))
{
foreach (var Mynumber in thatModel.IDlists)
{
using (SqlCommand cmd = new SqlCommand("InsertProces", con, tran))
{
cmd.CommandType = CommandType.StoredProcedure;
cmd.Parameters.Add(new SqlParameter { SqlDbType = SqlDbType.Int,
ParameterName = "one" }).Value = Mynumber;
cmd.Parameters.Add(new SqlParameter { SqlDbType = SqlDbType.Int,
ParameterName = "two" }).Value = thatModel.someprop;
cmd.Parameters.Add(new SqlParameter { SqlDbType = SqlDbType.Int,
ParameterName = "secnumber" }).Value = secName;// here i obtain the the result of the last transaction
using (SqlDataReader reader = cmd.ExecuteReader(CommandBehavior.SingleRow))
{
if (reader.HasRows)
{
reader.Read();
int theid = reader.GetInt32(0);
IDsList.Add(theid);
}
}
}
}
//if (thatModel.IDlists.Count == IDsList.Count)
//{
// return true;//or leave this alone in order to the root transaction scope complete
//DependingBlockingScope.RollBack();
//}
//else
//{
// throw new ArgumentException("no se consiguio el siguiente numero consecutivo", "SeqName");
//}
}
DependingBlockingScope.Complete();
}
scope.Complete();
}
}
catch (Exception ex)
{
if (ex is SqlException || ex is ArgumentException)
{
return false;
}
//roll back everyting and inform
}
return false;
}