View Javadoc

1   /*
2    * $Id:AbstractExternalTransactionTestCase.java 8215 2007-09-05 16:56:51Z aperepel $
3    * --------------------------------------------------------------------------------------
4    * Copyright (c) MuleSoft, Inc.  All rights reserved.  http://www.mulesoft.com
5    *
6    * The software in this package is published under the terms of the CPAL v1.0
7    * license, a copy of which has been included with this distribution in the
8    * LICENSE.txt file.
9    */
10  
11  package org.mule.transport.vm.functional.transactions;
12  
13  import org.mule.api.MessagingException;
14  import org.mule.api.MuleMessage;
15  import org.mule.api.transaction.TransactionCallback;
16  import org.mule.api.transaction.TransactionConfig;
17  import org.mule.module.client.MuleClient;
18  import org.mule.transaction.TransactionTemplate;
19  
20  import javax.transaction.Transaction;
21  
22  import org.apache.commons.logging.Log;
23  import org.apache.commons.logging.LogFactory;
24  
25  /** Test transaction behavior when "joinExternal" is set to allow joining external transactions
26   * There is one test per legal transactional behavior (e.g. ALWAYS_BEGIN).
27   */
28  public class ExternalTransactionTestCase extends AbstractExternalTransactionTestCase
29  {
30      public static final long WAIT = 3000L;
31  
32      protected static final Log logger = LogFactory.getLog(ExternalTransactionTestCase.class);
33  
34      @Override
35      protected String getConfigResources()
36      {
37          return "org/mule/test/config/external-transaction-config.xml";
38      }
39  
40      public void testBeginOrJoinTransaction() throws Exception
41      {
42          init();
43          TransactionTemplate<String> tt = createTransactionTemplate(TransactionConfig.ACTION_BEGIN_OR_JOIN, true);
44  
45          tm.begin();
46          final Transaction tx = tm.getTransaction();
47          final TestResource resource1 = new TestResource(tm);
48          tx.enlistResource(resource1);
49          assertNotNull(tx);
50          String result = tt.execute(new TransactionCallback<String>()
51          {
52              public String doInTransaction() throws Exception
53              {
54                  Transaction muleTx = tm.getTransaction();
55                  assertSame(tx, muleTx);
56                  resource1.setValue(14);
57                  return "OK";
58              }
59          });
60  
61          // Not committed yet, since Mule joined the external transaction
62          assertEquals("OK", result);
63          assertEquals(14, resource1.getValue());
64          assertEquals(0, resource1.getPersistentValue());
65          tm.commit();
66  
67          // Now it's committed
68          assertEquals(14, resource1.getPersistentValue());
69  
70          // now try with no active transaction
71          result = tt.execute(new TransactionCallback<String>()
72          {
73              public String doInTransaction() throws Exception
74              {
75                  Transaction muleTx = tm.getTransaction();
76                  muleTx.enlistResource(resource1);
77                  resource1.setValue(15);
78                  return "OK";
79              }
80          });
81  
82          // Mule began and committed the transaction
83          assertEquals(15, resource1.getPersistentValue());
84      }
85  
86      public void testBeginTransaction() throws Exception
87      {
88          init();
89          TransactionTemplate<String> tt = createTransactionTemplate(TransactionConfig.ACTION_ALWAYS_BEGIN, true);
90  
91          tm.begin();
92          final Transaction tx = tm.getTransaction();
93          final TestResource resource1 = new TestResource(tm);
94  
95          assertNotNull(tx);
96          String result = tt.execute(new TransactionCallback<String>()
97          {
98              public String doInTransaction() throws Exception
99              {
100                 Transaction muleTx = tm.getTransaction();
101                 assertNotSame(tx, muleTx);
102                 muleTx.enlistResource(resource1);
103                 resource1.setValue(14);
104                 return "OK";
105             }
106         });
107 
108         // Committed in Mule's transaction
109         assertEquals("OK", result);
110         assertEquals(14, resource1.getValue());
111         assertEquals(14, resource1.getPersistentValue());
112         tm.commit();
113 
114         // Now it's committed
115         assertEquals(14, resource1.getPersistentValue());
116 
117         result = tt.execute(new TransactionCallback<String>()
118         {
119             public String doInTransaction() throws Exception
120             {
121                 Transaction muleTx = tm.getTransaction();
122                 assertNotSame(tx, muleTx);
123                 muleTx.enlistResource(resource1);
124                 resource1.setValue(15);
125                 return "OK";
126             }
127         });
128 
129         // Committed in Mule's transaction
130         assertEquals("OK", result);
131         assertEquals(15, resource1.getPersistentValue());
132     }
133 
134     public void testNoTransactionProcessing() throws Exception
135     {
136         init();
137         TransactionTemplate<String> tt = createTransactionTemplate(TransactionConfig.ACTION_NONE, true);
138 
139         tm.begin();
140         final Transaction tx = tm.getTransaction();
141         final TestResource resource1 = new TestResource(tm);
142 
143         assertNotNull(tx);
144         tx.enlistResource(resource1);
145         resource1.setValue(14);
146         String result = tt.execute(new TransactionCallback<String>()
147         {
148             public String doInTransaction() throws Exception
149             {
150                 Transaction muleTx = tm.getTransaction();
151                 assertNull(muleTx);
152                 return "OK";
153             }
154         });
155 
156         // transaction restored, no commit
157         assertEquals("OK", result);
158         assertEquals(14, resource1.getValue());
159         assertEquals(0, resource1.getPersistentValue());
160         tm.commit();
161 
162         // Now it's committed
163         assertEquals(14, resource1.getPersistentValue());
164 
165         result = tt.execute(new TransactionCallback<String>()
166         {
167             public String doInTransaction() throws Exception
168             {
169                 Transaction muleTx = tm.getTransaction();
170                 assertNull(muleTx);
171                 return "OK";
172             }
173         });
174     }
175 
176     public void testAlwaysJoinTransaction() throws Exception
177     {
178         init();
179         TransactionTemplate<String> tt = createTransactionTemplate(TransactionConfig.ACTION_ALWAYS_JOIN, true);
180 
181         tm.begin();
182         final Transaction tx = tm.getTransaction();
183         final TestResource resource1 = new TestResource(tm);
184         tx.enlistResource(resource1);
185         assertNotNull(tx);
186         String result = tt.execute(new TransactionCallback<String>()
187         {
188             public String doInTransaction() throws Exception
189             {
190                 Transaction muleTx = tm.getTransaction();
191                 assertSame(tx, muleTx);
192                 resource1.setValue(14);
193                 return "OK";
194             }
195         });
196 
197         // Not committed yet, since Mule joined the external transaction
198         assertEquals("OK", result);
199         assertEquals(14, resource1.getValue());
200         assertEquals(0, resource1.getPersistentValue());
201         tm.commit();
202 
203         // Now it's committed
204         assertEquals(14, resource1.getPersistentValue());
205 
206         // try with no active transaction.. Should throw
207         Exception ex = null;
208         try
209         {
210             result = tt.execute(new TransactionCallback<String>()
211             {
212                 public String doInTransaction() throws Exception
213                 {
214                     return "OK";
215                 }
216             });
217             fail("No exception seen");
218         }
219         catch (Exception e)
220         {
221             ex = e;
222             logger.debug("saw exception " + e.getMessage());
223         }
224     }
225 
226     public void testJoinTransactionIfPossible() throws Exception
227     {
228         init();
229         TransactionTemplate<String> tt = createTransactionTemplate(TransactionConfig.ACTION_JOIN_IF_POSSIBLE, true);
230 
231         tm.begin();
232         final Transaction tx = tm.getTransaction();
233         final TestResource resource1 = new TestResource(tm);
234         tx.enlistResource(resource1);
235         assertNotNull(tx);
236         String result = tt.execute(new TransactionCallback<String>()
237         {
238             public String doInTransaction() throws Exception
239             {
240                 Transaction muleTx = tm.getTransaction();
241                 assertSame(tx, muleTx);
242                 resource1.setValue(14);
243                 return "OK";
244             }
245         });
246 
247         // Not committed yet, since Mule joined the external transaction
248         assertEquals("OK", result);
249         assertEquals(14, resource1.getValue());
250         assertEquals(0, resource1.getPersistentValue());
251         tm.commit();
252 
253         // Now it's committed
254         assertEquals(14, resource1.getPersistentValue());
255 
256         // try with no active transaction.. Should run with none
257         result = tt.execute(new TransactionCallback<String>()
258         {
259             public String doInTransaction() throws Exception
260             {
261                 Transaction muleTx = tm.getTransaction();
262                 assertNull(muleTx);
263                 return "OK";
264             }
265         });
266         assertEquals("OK", result);
267     }
268 
269     public void testNoTransactionAllowed() throws Exception
270     {
271         init();
272         TransactionTemplate<String> tt = createTransactionTemplate(TransactionConfig.ACTION_NEVER, true);
273 
274         tm.begin();
275         final Transaction tx = tm.getTransaction();
276         final TestResource resource1 = new TestResource(tm);
277         tx.enlistResource(resource1);
278         assertNotNull(tx);
279 
280         // This will throw since no transaction is allowed
281         Exception ex = null;
282         try
283         {
284             tt.execute(new TransactionCallback<String>()
285             {
286                 public String doInTransaction() throws Exception
287                 {
288                     return "OK";
289                 }
290             });
291             fail("No exception seen");
292         }
293         catch (Exception e)
294         {
295             ex = e;
296             logger.debug("saw exception " + e.getMessage());
297         }
298         tm.rollback();
299     }
300 
301     /** Check that the configuration specifies considers external transactions */
302     public void testConfiguration() throws Exception
303     {
304         MuleClient client = new MuleClient(muleContext);
305         tm = client.getMuleContext().getTransactionManager();
306         tm.begin();
307         client.send("vm://entry?connector=vm-normal", "OK", null);
308         tm.commit();
309         MuleMessage response = client.request("queue2", WAIT);
310         assertNull("Response is not null", response);
311 
312         // This will fail, since there will be no transaction to join
313         try
314         {
315             client.send("vm://entry?connector=vm-normal", "OK", null);
316             fail("Exception expected");
317         }
318         catch (MessagingException e)
319         {
320             // expected
321         }
322     }
323 }