@@ -35,53 +35,49 @@ public class KieSpringTransactionManager
3535
3636 public static final String RESOURCE_CONTAINER = "org.kie.resources" ;
3737
38- Logger logger = LoggerFactory .getLogger (getClass () );
38+ private static final Logger logger = LoggerFactory .getLogger (KieSpringTransactionManager . class );
3939 private AbstractPlatformTransactionManager ptm ;
4040
4141 TransactionDefinition td = new DefaultTransactionDefinition ();
42- TransactionStatus currentTransaction = null ;
42+ ThreadLocal < TransactionStatus > currentTransaction = new ThreadLocal <>() ;
4343
4444 public KieSpringTransactionManager (AbstractPlatformTransactionManager ptm ) {
4545 this .ptm = ptm ;
4646 }
4747
4848 public boolean begin () {
49- try {
50- // RHBPMS-4621 - transaction can be marked as rollback
51- // and still be associated with current thread
52- // See WFLY-4327
53- if (getStatus () == TransactionManager .STATUS_ROLLEDBACK ) {
54- logger .warn ("Cleaning up rolledback transaction" );
55- rollback (true );
56- }
57- if (getStatus () == TransactionManager .STATUS_NO_TRANSACTION ) {
58- // If there is no transaction then start one, we will commit within the same Command
59- // it seems in spring calling getTransaction is enough to begin a new transaction
60- currentTransaction = this .ptm .getTransaction (td );
61- return true ;
62- } else {
63- return false ;
49+ if (currentTransaction .get () == null ) {
50+ try {
51+ boolean activeTransaction = TransactionSynchronizationManager .isActualTransactionActive ();
52+ logger .info ("currentTransaction is null. Obtaining one" );
53+ currentTransaction .set (this .ptm .getTransaction (td ));
54+ return !activeTransaction || currentTransaction .get ().isNewTransaction ();
55+ } catch (Exception e ) {
56+ logger .warn ("Unable to begin transaction" , e );
57+ throw new RuntimeException ("Unable to begin transaction" , e );
6458 }
65- } catch (Exception e ) {
66- logger .warn ("Unable to begin transaction" ,
67- e );
68- throw new RuntimeException ("Unable to begin transaction" ,
69- e );
59+ } else {
60+ logger .debug ("current transaction is not null, reusing existing transaction" );
61+ return false ;
7062 }
7163 }
7264
7365 public void commit (boolean transactionOwner ) {
7466 if (!transactionOwner ) {
67+ logger .debug ("We are not the transaction owner, skipping commit" );
7568 return ;
7669 }
7770 if (!TransactionSynchronizationManager .isActualTransactionActive ()) {
7871 logger .warn ("transaction could not be commited as status is {}; check tx reaper timeout" , getStatus ());
7972 return ;
8073 }
8174
75+ if (currentTransaction .get () == null ) {
76+ logger .warn ("Out of order commit, no current transaction available" );
77+ return ;
78+ }
8279 try {
83- // if we didn't begin this transaction, then do nothing
84- this .ptm .commit (currentTransaction );
80+ this .ptm .commit (currentTransaction .get ());
8581 } catch (Exception e ) {
8682 logger .warn ("Unable to commit transaction" ,
8783 e );
@@ -90,19 +86,24 @@ public void commit(boolean transactionOwner) {
9086 } finally {
9187 cleanupTransaction ();
9288 }
93-
9489 }
9590
9691 public void rollback (boolean transactionOwner ) {
97- if (transactionOwner ) {
98- try {
99- this .ptm .rollback (currentTransaction );
100- } catch (Exception e ) {
101- logger .warn ("Unable to rollback transaction" , e );
102- throw new RuntimeException ("Unable to rollback transaction" , e );
103- } finally {
104- cleanupTransaction ();
105- }
92+ if (!transactionOwner ) {
93+ logger .debug ("We are not the transaction owner, skipping commit" );
94+ return ;
95+ }
96+ if (currentTransaction .get () == null ) {
97+ logger .warn ("Out of order rollback, no current transaction available" );
98+ return ;
99+ }
100+ try {
101+ this .ptm .rollback (currentTransaction .get ());
102+ } catch (Exception e ) {
103+ logger .warn ("Unable to rollback transaction" , e );
104+ throw new RuntimeException ("Unable to rollback transaction" , e );
105+ } finally {
106+ cleanupTransaction ();
106107 }
107108 }
108109
@@ -111,7 +112,8 @@ private void cleanupTransaction() {
111112 TransactionSynchronizationManager .unbindResource (KieSpringTransactionManager .RESOURCE_CONTAINER );
112113 }
113114 TransactionSynchronizationManager .clear ();
114- currentTransaction = null ;
115+ currentTransaction .remove ();
116+ logger .debug ("Transaction cleaned up" );
115117 }
116118
117119 /**
@@ -121,36 +123,34 @@ public int getStatus() {
121123 if (ptm == null ) {
122124 return TransactionManager .STATUS_NO_TRANSACTION ;
123125 }
124-
125126 logger .debug ("Current TX name (According to TransactionSynchronizationManager) : " + TransactionSynchronizationManager .getCurrentTransactionName ());
126127 if (TransactionSynchronizationManager .isActualTransactionActive ()) {
127128 TransactionStatus transaction = null ;
128129 try {
129- if (currentTransaction == null ) {
130+ if (currentTransaction .get () == null ) {
131+ logger .debug ("Get Status. Current transaction is null" );
130132 transaction = ptm .getTransaction (td );
133+ // If SynchronizationManager thinks it has an active transaction but
134+ // our transaction is a new one
135+ // then we must be in the middle of committing
136+
131137 if (transaction .isNewTransaction ()) {
138+ logger .debug ("Get Status. Commited transation" );
132139 return TransactionManager .STATUS_COMMITTED ;
133140 }
134141 } else {
135- transaction = currentTransaction ;
142+ transaction = currentTransaction . get () ;
136143 }
137144 logger .debug ("Current TX: " + transaction );
138- // If SynchronizationManager thinks it has an active transaction but
139- // our transaction is a new one
140- // then we must be in the middle of committing
141145 if (transaction .isCompleted ()) {
142146 if (transaction .isRollbackOnly ()) {
147+ logger .debug ("Get Status. Rolled back transation" );
143148 return TransactionManager .STATUS_ROLLEDBACK ;
144149 }
150+ logger .debug ("Get Status. Commited transaction" );
145151 return TransactionManager .STATUS_COMMITTED ;
146152 } else {
147- // Using the commented-out code in means that if rollback with this manager,
148- // I always have to catch and check the exception
149- // because ROLLEDBACK can mean both "rolled back" and "rollback only".
150- // if ( transaction.isRollbackOnly() ) {
151- // return TransactionManager.STATUS_ROLLEDBACK;
152- // }
153-
153+ logger .debug ("Get Status. Active transaction" );
154154 return TransactionManager .STATUS_ACTIVE ;
155155 }
156156 } finally {
0 commit comments