1 | |
|
2 | |
|
3 | |
|
4 | |
|
5 | |
|
6 | |
|
7 | |
|
8 | |
|
9 | |
|
10 | |
|
11 | |
package org.mule.tck; |
12 | |
|
13 | |
import org.mule.MuleManager; |
14 | |
import org.mule.impl.DefaultExceptionStrategy; |
15 | |
import org.mule.impl.MuleTransactionConfig; |
16 | |
import org.mule.transaction.TransactionCallback; |
17 | |
import org.mule.transaction.TransactionTemplate; |
18 | |
import org.mule.transaction.XaTransaction; |
19 | |
import org.mule.transaction.XaTransactionFactory; |
20 | |
import org.mule.umo.UMOTransactionConfig; |
21 | |
import org.mule.umo.manager.UMOTransactionManagerFactory; |
22 | |
|
23 | |
import javax.transaction.Status; |
24 | |
import javax.transaction.Transaction; |
25 | |
import javax.transaction.TransactionManager; |
26 | |
|
27 | |
|
28 | |
|
29 | |
|
30 | |
|
31 | 0 | public abstract class AbstractTxThreadAssociationTestCase extends AbstractMuleTestCase |
32 | |
{ |
33 | |
|
34 | |
private TransactionManager tm; |
35 | |
protected static final int TRANSACTION_TIMEOUT_SECONDS = 3; |
36 | |
|
37 | |
protected void doSetUp() throws Exception |
38 | |
{ |
39 | 0 | super.doSetUp(); |
40 | 0 | UMOTransactionManagerFactory factory = getTransactionManagerFactory(); |
41 | 0 | tm = factory.create(); |
42 | 0 | assertNotNull("Transaction Manager should be available.", tm); |
43 | 0 | assertNull("There sould be no current transaction associated.", tm.getTransaction()); |
44 | 0 | } |
45 | |
|
46 | |
public void testTxHandleCommitKeepsThreadAssociation() throws Exception |
47 | |
{ |
48 | |
|
49 | 0 | tm.setTransactionTimeout(TRANSACTION_TIMEOUT_SECONDS); |
50 | 0 | tm.begin(); |
51 | |
|
52 | 0 | Transaction tx = tm.getTransaction(); |
53 | 0 | assertNotNull("Transaction should have started.", tx); |
54 | 0 | assertEquals("TX should have been active", Status.STATUS_ACTIVE, tx.getStatus()); |
55 | |
|
56 | 0 | tx.commit(); |
57 | |
|
58 | 0 | tx = tm.getTransaction(); |
59 | 0 | assertNotNull("Committing via TX handle should NOT disassociated TX from the current thread.", |
60 | |
tx); |
61 | 0 | assertEquals("TX status should have been COMMITTED.", Status.STATUS_COMMITTED, tx.getStatus()); |
62 | |
|
63 | |
|
64 | |
|
65 | 0 | Transaction suspended = tm.suspend(); |
66 | 0 | assertTrue("Wrong TX suspended?.", suspended.equals(tx)); |
67 | 0 | assertNull("TX should've been disassociated from the thread.", tm.getTransaction()); |
68 | |
|
69 | |
|
70 | 0 | tm.resume(null); |
71 | |
|
72 | |
|
73 | 0 | assertNull(tm.getTransaction()); |
74 | 0 | } |
75 | |
|
76 | |
public void testTxManagerCommitDissassociatesThread() throws Exception |
77 | |
{ |
78 | |
|
79 | 0 | tm.setTransactionTimeout(TRANSACTION_TIMEOUT_SECONDS); |
80 | 0 | tm.begin(); |
81 | |
|
82 | 0 | Transaction tx = tm.getTransaction(); |
83 | 0 | assertNotNull("Transaction should have started.", tx); |
84 | 0 | assertEquals("TX should have been active", Status.STATUS_ACTIVE, tx.getStatus()); |
85 | |
|
86 | 0 | tm.commit(); |
87 | |
|
88 | 0 | assertNull("Committing via TX Manager should have disassociated TX from the current thread.", |
89 | |
tm.getTransaction()); |
90 | 0 | } |
91 | |
|
92 | |
public void testTxManagerRollbackDissassociatesThread() throws Exception |
93 | |
{ |
94 | |
|
95 | 0 | tm.setTransactionTimeout(TRANSACTION_TIMEOUT_SECONDS); |
96 | 0 | tm.begin(); |
97 | |
|
98 | 0 | Transaction tx = tm.getTransaction(); |
99 | 0 | assertNotNull("Transaction should have started.", tx); |
100 | 0 | assertEquals("TX should have been active", Status.STATUS_ACTIVE, tx.getStatus()); |
101 | |
|
102 | 0 | tm.rollback(); |
103 | |
|
104 | 0 | assertNull("Committing via TX Manager should have disassociated TX from the current thread.", |
105 | |
tm.getTransaction()); |
106 | 0 | } |
107 | |
|
108 | |
|
109 | |
|
110 | |
|
111 | |
|
112 | |
|
113 | |
public void testAlwaysBeginXaTransactionSuspendResume() throws Exception |
114 | |
{ |
115 | 0 | MuleManager.getInstance().setTransactionManager(tm); |
116 | 0 | assertNull("There sould be no current transaction associated.", tm.getTransaction()); |
117 | |
|
118 | |
|
119 | 0 | tm.setTransactionTimeout(TRANSACTION_TIMEOUT_SECONDS); |
120 | |
|
121 | |
|
122 | 0 | UMOTransactionConfig config = new MuleTransactionConfig(); |
123 | 0 | config.setFactory(new XaTransactionFactory()); |
124 | 0 | config.setAction(UMOTransactionConfig.ACTION_ALWAYS_BEGIN); |
125 | 0 | TransactionTemplate template = new TransactionTemplate(config, new DefaultExceptionStrategy()); |
126 | |
|
127 | |
|
128 | 0 | final UMOTransactionConfig nestedConfig = new MuleTransactionConfig(); |
129 | 0 | nestedConfig.setFactory(new XaTransactionFactory()); |
130 | 0 | nestedConfig.setAction(UMOTransactionConfig.ACTION_ALWAYS_BEGIN); |
131 | |
|
132 | |
|
133 | 0 | template.execute(new TransactionCallback() |
134 | |
{ |
135 | 0 | public Object doInTransaction() throws Exception |
136 | |
{ |
137 | |
|
138 | |
|
139 | 0 | TransactionTemplate nestedTemplate = |
140 | |
new TransactionTemplate(nestedConfig, new DefaultExceptionStrategy()); |
141 | 0 | final Transaction firstTx = tm.getTransaction(); |
142 | 0 | assertNotNull(firstTx); |
143 | 0 | assertEquals(firstTx.getStatus(), Status.STATUS_ACTIVE); |
144 | 0 | return nestedTemplate.execute(new TransactionCallback() |
145 | |
{ |
146 | 0 | public Object doInTransaction() throws Exception |
147 | |
{ |
148 | 0 | Transaction secondTx = tm.getTransaction(); |
149 | 0 | assertNotNull(secondTx); |
150 | 0 | assertEquals(firstTx.getStatus(), Status.STATUS_ACTIVE); |
151 | 0 | assertEquals(secondTx.getStatus(), Status.STATUS_ACTIVE); |
152 | |
try |
153 | |
{ |
154 | 0 | tm.resume(firstTx); |
155 | 0 | fail("Second transaction must be active"); |
156 | |
} |
157 | 0 | catch (java.lang.IllegalStateException e) |
158 | |
{ |
159 | |
|
160 | |
|
161 | |
|
162 | |
|
163 | 0 | } |
164 | |
try |
165 | |
{ |
166 | 0 | Transaction currentTx = tm.suspend(); |
167 | 0 | assertTrue(currentTx.equals(secondTx)); |
168 | 0 | tm.resume(firstTx); |
169 | 0 | assertEquals(firstTx, tm.getTransaction()); |
170 | 0 | assertEquals(firstTx.getStatus(), Status.STATUS_ACTIVE); |
171 | 0 | assertEquals(secondTx.getStatus(), Status.STATUS_ACTIVE); |
172 | 0 | Transaction a = tm.suspend(); |
173 | 0 | assertTrue(a.equals(firstTx)); |
174 | 0 | tm.resume(secondTx); |
175 | |
} |
176 | 0 | catch (Exception e) |
177 | |
{ |
178 | 0 | fail("Error: " + e); |
179 | 0 | } |
180 | |
|
181 | |
|
182 | 0 | return null; |
183 | |
} |
184 | |
}); |
185 | |
} |
186 | |
}); |
187 | 0 | assertNull("Committing via TX Manager should have disassociated TX from the current thread.", |
188 | |
tm.getTransaction()); |
189 | 0 | } |
190 | |
|
191 | |
|
192 | |
|
193 | |
|
194 | |
|
195 | |
|
196 | |
public void testXaTransactionTermination() throws Exception |
197 | |
{ |
198 | 0 | MuleManager.getInstance().setTransactionManager(tm); |
199 | 0 | assertNull("There sould be no current transaction associated.", tm.getTransaction()); |
200 | |
|
201 | |
|
202 | 0 | tm.setTransactionTimeout(TRANSACTION_TIMEOUT_SECONDS); |
203 | |
|
204 | 0 | XaTransaction muleTx = new XaTransaction(); |
205 | 0 | assertFalse(muleTx.isBegun()); |
206 | 0 | assertEquals(Status.STATUS_NO_TRANSACTION, muleTx.getStatus()); |
207 | 0 | muleTx.begin(); |
208 | |
|
209 | 0 | assertTrue(muleTx.isBegun()); |
210 | |
|
211 | 0 | muleTx.commit(); |
212 | |
|
213 | 0 | Transaction jtaTx = tm.getTransaction(); |
214 | 0 | assertNull("Committing via TX Manager should have disassociated TX from the current thread.", jtaTx); |
215 | 0 | assertEquals(Status.STATUS_NO_TRANSACTION, muleTx.getStatus()); |
216 | 0 | } |
217 | |
|
218 | |
|
219 | |
|
220 | |
|
221 | |
|
222 | |
|
223 | |
|
224 | |
public void testNoNestedTxStarted() throws Exception |
225 | |
{ |
226 | 0 | MuleManager.getInstance().setTransactionManager(tm); |
227 | 0 | assertNull("There sould be no current transaction associated.", tm.getTransaction()); |
228 | |
|
229 | |
|
230 | 0 | tm.setTransactionTimeout(TRANSACTION_TIMEOUT_SECONDS); |
231 | |
|
232 | |
|
233 | 0 | UMOTransactionConfig config = new MuleTransactionConfig(); |
234 | 0 | config.setFactory(new XaTransactionFactory()); |
235 | 0 | config.setAction(UMOTransactionConfig.ACTION_ALWAYS_BEGIN); |
236 | 0 | TransactionTemplate template = new TransactionTemplate(config, new DefaultExceptionStrategy()); |
237 | |
|
238 | |
|
239 | 0 | final UMOTransactionConfig nestedConfig = new MuleTransactionConfig(); |
240 | 0 | nestedConfig.setFactory(new XaTransactionFactory()); |
241 | 0 | nestedConfig.setAction(UMOTransactionConfig.ACTION_BEGIN_OR_JOIN); |
242 | |
|
243 | |
|
244 | 0 | template.execute(new TransactionCallback() |
245 | |
{ |
246 | 0 | public Object doInTransaction() throws Exception |
247 | |
{ |
248 | |
|
249 | |
|
250 | 0 | TransactionTemplate nestedTemplate = |
251 | |
new TransactionTemplate(nestedConfig, new DefaultExceptionStrategy()); |
252 | 0 | return nestedTemplate.execute(new TransactionCallback() |
253 | |
{ |
254 | 0 | public Object doInTransaction() throws Exception |
255 | |
{ |
256 | |
|
257 | 0 | return null; |
258 | |
} |
259 | |
}); |
260 | |
} |
261 | |
}); |
262 | 0 | } |
263 | |
|
264 | |
|
265 | |
protected TransactionManager getTransactionManager() |
266 | |
{ |
267 | 0 | return tm; |
268 | |
} |
269 | |
|
270 | |
protected abstract UMOTransactionManagerFactory getTransactionManagerFactory(); |
271 | |
|
272 | |
} |