带有线程的嵌套TransactionScope,带有和不带外部transactionScope

时间:2011-11-11 16:17:54

标签: .net transactionscope

我对数据库层进行了原子写入(插入,更新),将以多种方式调用:   有时它们会被原子地调用,在这种情况下代码必须创建一个新的环境事务   在其他情况下,可以从业务层中的父业务流程调用它们来启动事务范围,其中原子操作是必须全部在同一事务中的许多此类数据库操作之一。在这些情况下,操作必须在最外层事务范围使用语句创建的环境事务中登记。    最后,在某些情况下,最外层业务流程或最外层事务范围使用语句创建环境事务并运行多个线程来完成其工作,并且每个线程都执行必须在事务中的数据。在这些情况下,我需要使用DependentTransaction模式。 (在其他情况下,我使用单元测试中的这种模式,我希望整个过程不会在DB中留下永久的足迹)。

那么,我怎样(或者我应该)编写内部using语句(在嵌套的所有级别),以确保它在从外部事务调用时都能正常运行dependantTransaction,当它被自己调用并且没有环境事务时?

 private static readonly TransactionOptions txOptRC = 
   new TransactionOptions() { IsolationLevel = IsolationLevel.ReadCommitted };

 // need this when called by itself or from non-threaded outer Tx ... 
 using (var scop = new TransactionScope(TransactionScopeOption.Required, txOptRC))
 {
     // Transactional work here
     scop.Complete();
 }

 // need this when called from a multi-threaded or ThreadPooled outer Tx
 using (var scop = new TransactionScope(dependentTransaction))
 {
     // Transactional work here
     scop.Complete();
 }

我正在考虑的一种方法是:

 public void MyMethod( , , , , , DependentTransaction depTx = null)
 {
     using (var scop = depTx != null? 
         new TransactionScope(depTx):
         TransactionScope(TransactionScopeOption.Required, txOptRC))
     {
        // Transactional Work here
        scop.Complete();
     }
     // other stuff
 }

这会导致任何问题吗?

另外,(第二个问题)据我所知,这个克隆的依赖事务模式只在嵌套中需要在多个线程上调用从属(较低嵌套)事务工作或异步(在某种程度上)在内部嵌套事务投票之前,外部transactionScope代码无法完成并退出使用块的右括号的情况......

这是否意味着如果transactionScopes的内部嵌套(所有内容都是同步的并且在一个线程上),则不需要处理克隆的依赖事务?这种性质的内嵌式transactionScopes可以简单地使用标准结构吗?如果这是真的,我只需要在代码创建多个线程或者异步调用从属方法时使用上述条件语法......

1 个答案:

答案 0 :(得分:0)

一旦将外部事务作为参数获取,另一部分什么都得不到,我将有两个相同方法的重载。

你问题正文中的两个区块将成为那两个重载,然后我会把所有常用代码放在你刚刚调用它的时候:

// Transactional work here

进入类的私有方法,所以不要写两次。