1
2
3
4
5
6
7
8
9
10
11 package org.mule.module.jca;
12
13 import org.mule.DefaultMuleContext;
14 import org.mule.MessageExchangePattern;
15 import org.mule.api.MuleContext;
16 import org.mule.api.MuleException;
17 import org.mule.api.config.ConfigurationBuilder;
18 import org.mule.api.context.MuleContextBuilder;
19 import org.mule.api.endpoint.EndpointBuilder;
20 import org.mule.api.endpoint.InboundEndpoint;
21 import org.mule.api.model.Model;
22 import org.mule.api.service.Service;
23 import org.mule.api.source.CompositeMessageSource;
24 import org.mule.config.DefaultMuleConfiguration;
25 import org.mule.config.builders.DeployableMuleXmlContextListener;
26 import org.mule.config.spring.SpringXmlConfigurationBuilder;
27 import org.mule.context.DefaultMuleContextBuilder;
28 import org.mule.context.DefaultMuleContextFactory;
29 import org.mule.endpoint.EndpointURIEndpointBuilder;
30 import org.mule.endpoint.URIBuilder;
31 import org.mule.util.ClassUtils;
32
33 import java.io.IOException;
34 import java.io.ObjectInputStream;
35 import java.io.Serializable;
36 import java.util.HashMap;
37 import java.util.Map;
38
39 import javax.resource.NotSupportedException;
40 import javax.resource.ResourceException;
41 import javax.resource.spi.ActivationSpec;
42 import javax.resource.spi.BootstrapContext;
43 import javax.resource.spi.ResourceAdapter;
44 import javax.resource.spi.ResourceAdapterInternalException;
45 import javax.resource.spi.endpoint.MessageEndpointFactory;
46 import javax.transaction.xa.XAResource;
47
48 import org.apache.commons.logging.Log;
49 import org.apache.commons.logging.LogFactory;
50
51
52
53
54 public class MuleResourceAdapter implements ResourceAdapter, Serializable
55 {
56
57
58
59 private static final long serialVersionUID = 5727648958127416509L;
60
61
62
63
64 protected transient Log logger = LogFactory.getLog(this.getClass());
65
66 protected transient MuleContext muleContext;
67
68 protected transient BootstrapContext bootstrapContext;
69 protected final Map<MuleEndpointKey, Service> endpoints = new HashMap<MuleEndpointKey, Service>();
70 protected String defaultJcaModelName;
71
72 private String configurationBuilder = SpringXmlConfigurationBuilder.class.getName();
73 private String configurations;
74 private String username;
75 private String password;
76
77 private DefaultMuleConfiguration muleConfiguration = new DefaultMuleConfiguration();
78
79 private void readObject(ObjectInputStream ois) throws ClassNotFoundException, IOException
80 {
81 ois.defaultReadObject();
82 this.logger = LogFactory.getLog(this.getClass());
83 }
84
85
86
87
88 @Override
89 public void start(BootstrapContext bootstrapContext) throws ResourceAdapterInternalException
90 {
91 this.bootstrapContext = bootstrapContext;
92
93 if (configurations != null)
94 {
95 ConfigurationBuilder configBuilder = null;
96 try
97 {
98 configBuilder = (ConfigurationBuilder) ClassUtils.instanciateClass(configurationBuilder,
99 configurations);
100 }
101 catch (Exception e)
102 {
103 throw new ResourceAdapterInternalException(
104 "Failed to instanciate configurationBuilder class: " + configurationBuilder, e);
105 }
106
107 try
108 {
109 logger.info("Initializing Mule...");
110
111 MuleContextBuilder contextBuilder = new DefaultMuleContextBuilder();
112 muleConfiguration.setSystemModelType(JcaModel.JCA_MODEL_TYPE);
113 contextBuilder.setMuleConfiguration(muleConfiguration);
114 muleContext = new DefaultMuleContextFactory().createMuleContext(configBuilder, contextBuilder);
115
116
117
118
119 DeployableMuleXmlContextListener.setMuleContext(muleContext);
120 }
121 catch (MuleException e)
122 {
123 logger.error(e);
124 throw new ResourceAdapterInternalException(
125 "Failed to load configurations: " + configurations, e);
126 }
127 try
128 {
129 logger.info("Starting Mule...");
130 muleContext.start();
131 }
132 catch (MuleException e)
133 {
134 logger.error(e);
135 throw new ResourceAdapterInternalException("Failed to start management context", e);
136 }
137 }
138 }
139
140
141
142
143 @Override
144 public void stop()
145 {
146 logger.info("Stopping Mule...");
147 muleContext.dispose();
148 muleContext = null;
149 bootstrapContext = null;
150 }
151
152
153
154
155 public BootstrapContext getBootstrapContext()
156 {
157 return bootstrapContext;
158 }
159
160
161
162
163
164 @Override
165 public void endpointActivation(MessageEndpointFactory endpointFactory, ActivationSpec activationSpec)
166 throws ResourceException
167 {
168 if (activationSpec.getResourceAdapter() != this)
169 {
170 throw new ResourceException("ActivationSpec not initialized with this ResourceAdapter instance");
171 }
172
173 if (activationSpec.getClass().equals(MuleActivationSpec.class))
174 {
175 MuleActivationSpec muleActivationSpec = (MuleActivationSpec) activationSpec;
176 try
177 {
178
179 String modelName = resolveModelName(muleActivationSpec);
180
181
182 JcaModel model = getJcaModel(modelName);
183
184
185 InboundEndpoint endpoint = createMessageInflowEndpoint(muleActivationSpec);
186
187
188 Service service = createJcaService(endpointFactory, model, endpoint);
189
190
191 MuleEndpointKey key = new MuleEndpointKey(endpointFactory, muleActivationSpec);
192 endpoints.put(key, service);
193 }
194 catch (Exception e)
195 {
196 logger.error(e.getMessage(), e);
197 }
198 }
199 else
200 {
201 throw new NotSupportedException("That type of ActicationSpec not supported: "
202 + activationSpec.getClass());
203 }
204
205 }
206
207
208
209
210
211 @Override
212 public void endpointDeactivation(MessageEndpointFactory endpointFactory, ActivationSpec activationSpec)
213 {
214 if (activationSpec.getClass().equals(MuleActivationSpec.class))
215 {
216 MuleActivationSpec muleActivationSpec = (MuleActivationSpec) activationSpec;
217 MuleEndpointKey key = new MuleEndpointKey(endpointFactory, (MuleActivationSpec) activationSpec);
218 Service service = endpoints.remove(key);
219 if (service == null)
220 {
221 logger.warn("No endpoint was registered with key: " + key);
222 return;
223 }
224
225
226 String modelName = null;
227 try
228 {
229 modelName = resolveModelName(muleActivationSpec);
230 }
231 catch (ResourceException e)
232 {
233 logger.error(e.getMessage(), e);
234 }
235
236 try
237 {
238 muleContext.getRegistry().unregisterService(service.getName());
239 }
240 catch (MuleException e)
241 {
242 logger.error(e.getMessage(), e);
243 }
244 }
245 }
246
247 protected String resolveModelName(MuleActivationSpec activationSpec) throws ResourceException
248 {
249
250
251
252 String modelName = activationSpec.getModelName();
253 if (modelName == null)
254 {
255 modelName = defaultJcaModelName;
256 }
257 if (modelName == null)
258 {
259 throw new ResourceException(
260 "The 'modelName' property has not been configured for either the MuleResourceAdaptor or MuleActicationSpec.");
261 }
262 return modelName;
263 }
264
265 protected JcaModel getJcaModel(String modelName) throws MuleException, ResourceException
266 {
267 Model model = muleContext.getRegistry().lookupModel(modelName);
268 if (model != null)
269 {
270 if (model instanceof JcaModel)
271 {
272 return (JcaModel) model;
273 }
274 else
275 {
276 throw new ResourceException("Model:-" + modelName + " is not compatible with JCA type");
277 }
278 }
279 else
280 {
281 JcaModel jcaModel = new JcaModel();
282 jcaModel.setName(modelName);
283 muleContext.getRegistry().registerModel(jcaModel);
284 return jcaModel;
285 }
286 }
287
288 protected Service createJcaService(MessageEndpointFactory endpointFactory,
289 JcaModel model,
290 InboundEndpoint endpoint) throws MuleException
291 {
292 String name = "JcaService#" + endpointFactory.hashCode();
293 Service service = new JcaService(muleContext);
294 service.setName(name);
295 ((CompositeMessageSource) service.getMessageSource()).addSource(endpoint);
296
297
298
299
300 service.setComponent(new JcaComponent(endpointFactory, model.getEntryPointResolverSet(), service,
301 new DelegateWorkManager(bootstrapContext.getWorkManager())));
302 service.setModel(model);
303 muleContext.getRegistry().registerService(service);
304 return service;
305 }
306
307 protected InboundEndpoint createMessageInflowEndpoint(MuleActivationSpec muleActivationSpec)
308 throws MuleException
309 {
310 EndpointBuilder endpointBuilder = new EndpointURIEndpointBuilder(new URIBuilder(
311 muleActivationSpec.getEndpoint(), muleContext));
312
313 endpointBuilder.setExchangePattern(MessageExchangePattern.ONE_WAY);
314
315 return muleContext.getEndpointFactory().getInboundEndpoint(endpointBuilder);
316 }
317
318
319
320
321
322
323
324 @Override
325 public XAResource[] getXAResources(ActivationSpec[] activationSpecs) throws ResourceException
326 {
327 return new XAResource[]{};
328 }
329
330
331
332
333 public void setPassword(String password)
334 {
335 this.password = password;
336 }
337
338
339
340
341 public void setConfigurations(String configurations)
342 {
343 this.configurations = configurations;
344 }
345
346
347
348
349 public void setUserName(String userid)
350 {
351 this.username = userid;
352 }
353
354 public void setConfigurationBuilder(String configbuilder)
355 {
356 this.configurationBuilder = configbuilder;
357 }
358
359 public void setModelName(String modelName)
360 {
361 this.defaultJcaModelName = modelName;
362 }
363
364 public void setAutoWrapMessageAwareTransform(Boolean autoWrapMessageAwareTransform)
365 {
366 if (autoWrapMessageAwareTransform != null)
367 {
368 muleConfiguration.setAutoWrapMessageAwareTransform(autoWrapMessageAwareTransform);
369 }
370 }
371
372 public void setCacheMessageAsBytes(Boolean cacheMessageAsBytes)
373 {
374 if (cacheMessageAsBytes != null)
375 {
376 muleConfiguration.setCacheMessageAsBytes(cacheMessageAsBytes);
377 }
378 }
379
380 public void setCacheMessageOriginalPayload(Boolean cacheMessageOriginalPayload)
381 {
382 if (cacheMessageOriginalPayload != null)
383 {
384 muleConfiguration.setCacheMessageOriginalPayload(cacheMessageOriginalPayload);
385 }
386 }
387
388 public void setClusterId(String clusterId)
389 {
390 ((DefaultMuleContext) muleContext).setClusterId(clusterId);
391 }
392
393 public void setDefaultEncoding(String encoding)
394 {
395 muleConfiguration.setDefaultEncoding(encoding);
396 }
397
398 public void setDefaultQueueTimeout(Integer defaultQueueTimeout)
399 {
400 if (defaultQueueTimeout != null)
401 {
402 muleConfiguration.setDefaultQueueTimeout(defaultQueueTimeout);
403 }
404 }
405
406 public void setDefaultResponseTimeout(Integer responseTimeout)
407 {
408 if (responseTimeout != null)
409 {
410 muleConfiguration.setDefaultResponseTimeout(responseTimeout);
411 }
412 }
413
414 public void setDefaultSynchronousEndpoints(Boolean synchronous)
415 {
416 if (synchronous != null)
417 {
418 muleConfiguration.setDefaultSynchronousEndpoints(synchronous);
419 }
420 }
421
422 public void setDefaultTransactionTimeout(Integer defaultTransactionTimeout)
423 {
424 if (defaultTransactionTimeout != null)
425 {
426 muleConfiguration.setDefaultTransactionTimeout(defaultTransactionTimeout);
427 }
428 }
429
430 public void setDomainId(String domainId)
431 {
432 muleConfiguration.setDomainId(domainId);
433 }
434
435 public void setServerId(String serverId)
436 {
437 muleConfiguration.setId(serverId);
438 }
439
440 public void setShutdownTimeout(Integer shutdownTimeout)
441 {
442 if (shutdownTimeout != null)
443 {
444 muleConfiguration.setShutdownTimeout(shutdownTimeout);
445 }
446 }
447
448 public void setWorkingDirectory(String workingDirectory)
449 {
450 muleConfiguration.setWorkingDirectory(workingDirectory);
451 }
452
453
454
455
456 public String getConfigurationBuilder()
457 {
458 return configurationBuilder;
459 }
460
461 public String getConfigurations()
462 {
463 return configurations;
464 }
465
466 public String getUserName()
467 {
468 return username;
469 }
470
471 public String getPassword()
472 {
473 return password;
474 }
475
476 public String getModelName()
477 {
478 return defaultJcaModelName;
479 }
480
481 public String getClusterId()
482 {
483 return muleContext.getClusterId();
484 }
485
486 public String getDefaultEncoding()
487 {
488 return muleConfiguration.getDefaultEncoding();
489 }
490
491 public int getDefaultQueueTimeout()
492 {
493 return muleConfiguration.getDefaultQueueTimeout();
494 }
495
496 public int getDefaultResponseTimeout()
497 {
498 return muleConfiguration.getDefaultResponseTimeout();
499 }
500
501 public int getDefaultTransactionTimeout()
502 {
503 return muleConfiguration.getDefaultTransactionTimeout();
504 }
505
506 public String getDomainId()
507 {
508 return muleConfiguration.getDomainId();
509 }
510
511 public String getId()
512 {
513 return muleConfiguration.getId();
514 }
515
516 public String getMuleHomeDirectory()
517 {
518 return muleConfiguration.getMuleHomeDirectory();
519 }
520
521 public int getShutdownTimeout()
522 {
523 return muleConfiguration.getShutdownTimeout();
524 }
525
526 public String getSystemModelType()
527 {
528 return muleConfiguration.getSystemModelType();
529 }
530
531 public String getSystemName()
532 {
533 return muleConfiguration.getSystemName();
534 }
535
536 public String getWorkingDirectory()
537 {
538 return muleConfiguration.getWorkingDirectory();
539 }
540
541 public boolean isAutoWrapMessageAwareTransform()
542 {
543 return muleConfiguration.isAutoWrapMessageAwareTransform();
544 }
545
546 public boolean isCacheMessageAsBytes()
547 {
548 return muleConfiguration.isCacheMessageAsBytes();
549 }
550
551 public boolean isCacheMessageOriginalPayload()
552 {
553 return muleConfiguration.isCacheMessageOriginalPayload();
554 }
555
556 public boolean isClientMode()
557 {
558 return muleConfiguration.isClientMode();
559 }
560
561 public boolean isEnableStreaming()
562 {
563 return muleConfiguration.isEnableStreaming();
564 }
565
566 @Override
567 public int hashCode()
568 {
569 final int prime = 31;
570 int result = 1;
571 result = prime * result + ((configurationBuilder == null) ? 0 : configurationBuilder.hashCode());
572 result = prime * result + ((configurations == null) ? 0 : configurations.hashCode());
573 result = prime * result + ((defaultJcaModelName == null) ? 0 : defaultJcaModelName.hashCode());
574 result = prime * result + ((endpoints == null) ? 0 : endpoints.hashCode());
575 result = prime * result + ((muleConfiguration == null) ? 0 : muleConfiguration.hashCode());
576 result = prime * result + ((password == null) ? 0 : password.hashCode());
577 result = prime * result + ((username == null) ? 0 : username.hashCode());
578 return result;
579 }
580
581 @Override
582 public boolean equals(Object obj)
583 {
584 if (this == obj) return true;
585 if (obj == null) return false;
586 if (getClass() != obj.getClass()) return false;
587 MuleResourceAdapter other = (MuleResourceAdapter) obj;
588 if (configurationBuilder == null)
589 {
590 if (other.configurationBuilder != null) return false;
591 }
592 else if (!configurationBuilder.equals(other.configurationBuilder)) return false;
593 if (configurations == null)
594 {
595 if (other.configurations != null) return false;
596 }
597 else if (!configurations.equals(other.configurations)) return false;
598 if (defaultJcaModelName == null)
599 {
600 if (other.defaultJcaModelName != null) return false;
601 }
602 else if (!defaultJcaModelName.equals(other.defaultJcaModelName)) return false;
603 if (endpoints == null)
604 {
605 if (other.endpoints != null) return false;
606 }
607 else if (!endpoints.equals(other.endpoints)) return false;
608 if (muleConfiguration == null)
609 {
610 if (other.muleConfiguration != null) return false;
611 }
612 else if (!muleConfiguration.equals(other.muleConfiguration)) return false;
613 if (password == null)
614 {
615 if (other.password != null) return false;
616 }
617 else if (!password.equals(other.password)) return false;
618 if (username == null)
619 {
620 if (other.username != null) return false;
621 }
622 else if (!username.equals(other.username)) return false;
623 return true;
624 }
625
626 }