ケース2春のトランザクションエラー

デフォルトのトランザクションモードを使用します

  ためにJavaの設計のために、それが継承のRuntimeExceptionの例外は、IOExceptionを通り、「checkException」または一般的な異常であると見なされていない、Javaの構文でこれらの例外は必須のプロセスです。これらの一般的な異常のために、春は、それらはデフォルトで処理されているので、デフォルトではロールバックされません。あなたはロールバックされているすべての例外を表すためにrollbackfor = Exception.classを追加することができます。

内線通話

  取引にクラスのトランザクション呼び出し方法ない方法はロールバックされません。この方法は、直接介して、そのようなコール取引に取引することなくメソッドである場合、ロールバックは、プロキシモードを生成するので、ばねが使用されるthis.xxx()エージェントのトランザクションを発生させることなくコールので、トランザクションは動作しません。一般的な解決策、クラスの解散。

  トランザクション処理Aにおける春の呼び出しが別の保留中のトランザクションを持っており、あなたは、このメソッドBを呼び出すためにこれを使用する場合は、新しいトランザクションメソッドBを作成し、 
この時間の方法Bは、今回の方法Bをゲームをくぼみましたトランザクションは失敗します。そして、ロールバックされません。 

  • PROPAGATION_REQUIRED:トランザクション、現在のトランザクションのサポートがある場合。何のトランザクションが開いて取引されていない場合。
  • PROPAGATION_REQUIRES_NEW:常に新しいビジネスを始めます。トランザクションがすでに存在する場合は、既存のトランザクションが保留中。

次のように:

@Service
 パブリック クラスEmployeeService { 
 
    @Autowired 
    プライベートEmployeeDao EmployeeDao; 
 
    公共 無効保存(){
         試み{        
             この .saveEmployee();   // この呼び出しがトランザクションをオンにしない、データが保存されている 
        } キャッチ(例外E){ 
            EをprintStackTrace(); 
        } 
    } 
    
    @Transactional(伝播 = Propagation.PROPAGATION_REQUIRED)
     // ここでかPROPAGATION_REQUIRED PROPAGATION_REQUIRES_NEW、トランザクション有効にならない
    公共 ボイドsaveEmployee(){ 
        従業員= 新しい従業員()。
        employee.setName( "zhangsan" ); 
        employee.setAge( "26" ; 
        employeeDao.save(従業員); 
        スロー 新しいのRuntimeExceptionを(); 
    } 
}

问题原因:

JDKダイナミックプロキシ。場合にのみ、トランザクションは直接呼び出される動的プロキシを生成します。SpringIoC容器内に返されたオブジェクトの呼び出しではなく、実際のオブジェクトのプロキシオブジェクトです。そして、ここでこれはEmployeeService実際のオブジェクトではなく、プロキシオブジェクト。

解决办法:

デフォルトのトランザクションまたはトランザクションなしでプロセスBにおけるオープン・トランザクションのための、請求項1の方法、および方法Aキャッチthrow new RuntimeException();(指定されていないrollbackFor、デフォルトのロールバックの異常RuntimeException)、そのような使用は、方法トランザクションです。(必要がありますがthrow new RuntimeException();それ以外の場合は例外が取得プロセスは、同じことがロールバックされません、です。)次のように:

@Transactional()// トランザクションを回す
公共 のボイド保存(){
     試み{        
         この ; .saveEmployee()   // この呼び出しトランザクションが失敗する場合は、データが保存されます 
    } キャッチ(例外E){ 
        e.printStackTrace(); 
        スロー 新しい新規のRuntimeException(); 
    } 
}

方法2は、方法Aは、トランザクションにトランザクション開く手順B、Aをオンにしないことがあり、これは動的メソッドコールエージェント(に呼び出すAopContext.currentProxy()次のように)。

公共の 無効(){保存
     してみてください{         
        EmployeeServiceプロキシ = (EmployeeService)AopContext.currentProxy(); 
        proxy.saveEmployee(); 
    } キャッチ(例外e){ 
        e.printStackTrace(); 
    } 
}

 

 

参考:トランザクション春の障害が発生した2例

参考:トランザクションが失敗した理由これを呼び出すために使用される春

参考:一つの理由Springのトランザクション障害(この呼び出し)

おすすめ

転載: www.cnblogs.com/heqiyoujing/p/11221093.html