2017-07-18 14 views
0

私は、グローバルトランザクションに関わるEJBを持っています。 失敗した場合、トランザクション全体が失敗することは望ましくありませんが、明示的にロールバックしたいというコードの一部があります。ロールバックがCMTで禁じられていたよう分散トランザクションにおける正当なロールバック:可能ですか?

は私がBMTを作成し、次のコードを試してみました:私はちょうど私の地元デシベルの変更を元に戻すが、私はまた、これが外部に失敗し伝播しない

connection.setAutoCommit(false); 
Savepoint sp= connection.setSavepoint(); 
try{ 
    //my code editing DB that could possibly fail 
}catch(SomeException ex){ 
    connection.rollback(sp); 
} 

この道を。とにかく、このプログラムでは、のようにして失敗します。

「セーブポイントが分散トランザクションに禁止されている」この問題を解決するための別のアプローチがありますか?

答えて

1

トランザクションコンテキストはBTMに伝播されません。あなたのBeanはグローバルトランザクションの一部でもありません。したがって、グローバルトランザクションが失敗した場合、変更はまだコミットされる可能性があります。

websphereの設定に慣れていませんが、接続が再確認されます。私はBTMに注入されることを期待しているか、CMTから何とか接続を渡しますか?接続がjta /グローバルトランザクションをサポートするように設定されている場合は、コンテナの設定を確認しようとする可能性があります。 接続を開始する前に、UserTransaction.begin()を起動しますか? これでも問題が解決しない場合は、

ネストされたトランザクションを使用していますが、Java EEではサポートされていません。ちょうどWebShereがプロバイダを特定の方法で実行する方法がある(私はその能力を知らない)。

最も簡単な方法は、CMT REQUIRES_NEWですが、グローバルトランザクションがロールバックされてもdb変更がコミットされるという欠点があります。

アプリケーションを変更する必要があるかもしれません。

2

@TransactionAttribute(REQUIRES_NEW)と注釈が付けられた2番目のEJBを使用してCMTを使用すると、失敗する可能性のあるコードを置くことができます。このEJBを他のEJBから呼び出す必要があります。

コンテナはコードの新しいトランザクションを作成し、失敗した場合はロールバックします。

+0

新しいトランザクションは、それが動作すればコミットします。新しいトランザクションは最初のトランザクションとは独立していることに注意してください。何かが最初のトランザクションをロールバックすると(別の理由で)新しいピースがコミットされます。 – kaczyns

関連する問題