1
2
3
4
5
6
7
8
9
10
11 package org.mule.registry;
12
13 import org.mule.api.MuleContext;
14 import org.mule.api.MuleException;
15 import org.mule.api.NameableObject;
16 import org.mule.api.agent.Agent;
17 import org.mule.api.config.MuleProperties;
18 import org.mule.api.construct.FlowConstruct;
19 import org.mule.api.endpoint.EndpointBuilder;
20 import org.mule.api.endpoint.EndpointFactory;
21 import org.mule.api.endpoint.ImmutableEndpoint;
22 import org.mule.api.lifecycle.Disposable;
23 import org.mule.api.lifecycle.Initialisable;
24 import org.mule.api.lifecycle.InitialisationException;
25 import org.mule.api.lifecycle.LifecycleException;
26 import org.mule.api.model.Model;
27 import org.mule.api.registry.AbstractServiceDescriptor;
28 import org.mule.api.registry.MuleRegistry;
29 import org.mule.api.registry.RegistrationException;
30 import org.mule.api.registry.ResolverException;
31 import org.mule.api.registry.ServiceDescriptor;
32 import org.mule.api.registry.ServiceDescriptorFactory;
33 import org.mule.api.registry.ServiceException;
34 import org.mule.api.registry.ServiceType;
35 import org.mule.api.registry.TransformerResolver;
36 import org.mule.api.service.Service;
37 import org.mule.api.transformer.DataType;
38 import org.mule.api.transformer.DiscoverableTransformer;
39 import org.mule.api.transformer.Transformer;
40 import org.mule.api.transformer.TransformerException;
41 import org.mule.api.transport.Connector;
42 import org.mule.config.i18n.CoreMessages;
43 import org.mule.transformer.types.SimpleDataType;
44 import org.mule.util.SpiUtils;
45 import org.mule.util.StringUtils;
46 import org.mule.util.UUID;
47
48 import java.util.ArrayList;
49 import java.util.Collection;
50 import java.util.Collections;
51 import java.util.Comparator;
52 import java.util.Iterator;
53 import java.util.List;
54 import java.util.Map;
55 import java.util.Properties;
56 import java.util.concurrent.ConcurrentHashMap;
57
58 import org.apache.commons.logging.Log;
59 import org.apache.commons.logging.LogFactory;
60
61
62
63
64
65 public class MuleRegistryHelper implements MuleRegistry
66 {
67 protected transient Log logger = LogFactory.getLog(MuleRegistryHelper.class);
68
69
70
71
72 private DefaultRegistryBroker registry;
73
74
75
76
77 protected ConcurrentHashMap
78 protected ConcurrentHashMap
79
80 private MuleContext muleContext;
81
82 public MuleRegistryHelper(DefaultRegistryBroker registry, MuleContext muleContext)
83 {
84 this.registry = registry;
85 this.muleContext = muleContext;
86 }
87
88
89
90
91 public void initialise() throws InitialisationException
92 {
93
94
95
96
97 }
98
99
100
101
102 public void dispose()
103 {
104 transformerListCache.clear();
105 exactTransformerCache.clear();
106 }
107
108 public void fireLifecycle(String phase) throws LifecycleException
109 {
110 if(Initialisable.PHASE_NAME.equals(phase))
111 {
112 registry.initialise();
113 }
114 else if(Disposable.PHASE_NAME.equals(phase))
115 {
116 registry.dispose();
117 }
118 else
119 {
120 registry.fireLifecycle(phase);
121 }
122 }
123
124
125
126
127 public Connector lookupConnector(String name)
128 {
129 return (Connector) registry.lookupObject(name);
130 }
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166 public EndpointBuilder lookupEndpointBuilder(String name)
167 {
168 Object o = registry.lookupObject(name);
169 if (o instanceof EndpointBuilder)
170 {
171 logger.debug("Global endpoint EndpointBuilder for name: " + name + " found");
172 return (EndpointBuilder) o;
173 }
174 else
175 {
176 logger.debug("No endpoint builder with the name: " + name + " found.");
177 return null;
178 }
179 }
180
181
182
183
184 public EndpointFactory lookupEndpointFactory()
185 {
186 return (EndpointFactory) registry.lookupObject(MuleProperties.OBJECT_MULE_ENDPOINT_FACTORY);
187 }
188
189
190
191
192 public Transformer lookupTransformer(String name)
193 {
194 return (Transformer) registry.lookupObject(name);
195 }
196
197
198
199
200
201
202
203
204 @Deprecated
205 public Transformer lookupTransformer(Class inputType, Class outputType) throws TransformerException
206 {
207 return lookupTransformer(new SimpleDataType(inputType), new SimpleDataType(outputType));
208 }
209
210
211
212
213
214
215
216
217 @Deprecated
218 public List<Transformer> lookupTransformers(Class input, Class output)
219 {
220 return lookupTransformers(new SimpleDataType(input), new SimpleDataType(output));
221 }
222
223
224
225
226 public Transformer lookupTransformer(DataType source, DataType result) throws TransformerException
227 {
228 final String dataTypePairHash = getDataTypeSourceResultPairHash(source, result);
229 Transformer cachedTransformer = (Transformer) exactTransformerCache.get(dataTypePairHash);
230 if (cachedTransformer != null)
231 {
232 return cachedTransformer;
233 }
234
235 Transformer trans = resolveTransformer(source, result);
236
237 if (trans != null)
238 {
239 Transformer concurrentlyAddedTransformer = (Transformer) exactTransformerCache.putIfAbsent(
240 dataTypePairHash, trans);
241 if (concurrentlyAddedTransformer != null)
242 {
243 return concurrentlyAddedTransformer;
244 }
245 else
246 {
247 return trans;
248 }
249 }
250 else
251 {
252 throw new TransformerException(CoreMessages.noTransformerFoundForMessage(source, result));
253 }
254 }
255
256 protected Transformer resolveTransformer(DataType source, DataType result) throws TransformerException
257 {
258 List<TransformerResolver> resolvers = (List<TransformerResolver>) lookupObjects(TransformerResolver.class);
259 Collections.sort(resolvers, new TransformerResolverComparator());
260
261 for (TransformerResolver resolver : resolvers)
262 {
263 try
264 {
265 Transformer trans = resolver.resolve(source, result);
266 if (trans != null)
267 {
268 return trans;
269 }
270 }
271 catch (ResolverException e)
272 {
273 throw new TransformerException(CoreMessages.noTransformerFoundForMessage(source, result), e);
274 }
275 }
276 return null;
277 }
278
279
280
281
282 public List<Transformer> lookupTransformers(DataType source, DataType result)
283 {
284 final String dataTypePairHash = getDataTypeSourceResultPairHash(source, result);
285
286 List<Transformer> results = (List<Transformer>) transformerListCache.get(dataTypePairHash);
287 if (results != null)
288 {
289 return results;
290 }
291
292 results = new ArrayList<Transformer>(2);
293 Collection<Transformer> transformers = registry.lookupObjects(Transformer.class);
294 for (Transformer t : transformers)
295 {
296
297
298
299 if (!(t instanceof DiscoverableTransformer))
300 {
301 continue;
302 }
303 DataType dt = t.getReturnDataType();
304 if (result.isCompatibleWith(dt) && t.isSourceDataTypeSupported(source))
305 {
306 results.add(t);
307 }
308 }
309
310 List<Transformer> concurrentlyAddedTransformers = (List<Transformer>) transformerListCache.putIfAbsent(
311 dataTypePairHash, results);
312 if (concurrentlyAddedTransformers != null)
313 {
314 return concurrentlyAddedTransformers;
315 }
316 else
317 {
318 return results;
319 }
320 }
321
322
323
324
325 public Model lookupModel(String name)
326 {
327 return (Model) registry.lookupObject(name);
328 }
329
330
331
332
333 public Model lookupSystemModel()
334 {
335 return lookupModel(MuleProperties.OBJECT_SYSTEM_MODEL);
336 }
337
338
339
340
341 public Collection<Model> getModels()
342 {
343 return registry.lookupObjects(Model.class);
344 }
345
346
347
348
349 public Collection<Connector> getConnectors()
350 {
351 return registry.lookupObjects(Connector.class);
352 }
353
354
355
356
357 public Collection<Agent> getAgents()
358 {
359 return registry.lookupObjects(Agent.class);
360 }
361
362
363
364
365 public Collection<ImmutableEndpoint> getEndpoints()
366 {
367 return registry.lookupObjects(ImmutableEndpoint.class);
368 }
369
370
371
372
373 public Collection<Transformer> getTransformers()
374 {
375 return registry.lookupObjects(Transformer.class);
376 }
377
378
379
380
381 public Agent lookupAgent(String name)
382 {
383 return (Agent) registry.lookupObject(name);
384 }
385
386
387
388
389 public Service lookupService(String name)
390 {
391 return (Service) registry.lookupObject(name);
392 }
393
394
395
396
397 public Collection<Service> lookupServices()
398 {
399 return lookupObjects(Service.class);
400 }
401
402
403
404
405 public Collection<Service> lookupServices(String model)
406 {
407 Collection<Service> services = lookupServices();
408 List<Service> modelServices = new ArrayList<Service>();
409 Iterator it = services.iterator();
410 Service service;
411 while (it.hasNext())
412 {
413 service = (Service) it.next();
414 if (model.equals(service.getModel().getName()))
415 {
416 modelServices.add(service);
417 }
418 }
419 return modelServices;
420 }
421
422
423
424
425 public FlowConstruct lookupFlowConstruct(String name)
426 {
427 return (FlowConstruct) registry.lookupObject(name);
428 }
429
430
431
432
433 public Collection<FlowConstruct> lookupFlowConstructs()
434 {
435 return lookupObjects(FlowConstruct.class);
436 }
437
438
439
440
441 public final void registerTransformer(Transformer transformer) throws MuleException
442 {
443 registry.registerObject(getName(transformer), transformer, Transformer.class);
444 notifyTransformerResolvers(transformer, TransformerResolver.RegistryAction.ADDED);
445 }
446
447 protected void notifyTransformerResolvers(Transformer t, TransformerResolver.RegistryAction action)
448 {
449 if (t instanceof DiscoverableTransformer)
450 {
451 Collection<TransformerResolver> resolvers = lookupObjects(TransformerResolver.class);
452 for (TransformerResolver resolver : resolvers)
453 {
454 resolver.transformerChange(t, action);
455 }
456 transformerListCache.clear();
457 exactTransformerCache.clear();
458 }
459 }
460
461
462
463
464 public ServiceDescriptor lookupServiceDescriptor(ServiceType type, String name, Properties overrides) throws ServiceException
465 {
466 String key = new AbstractServiceDescriptor.Key(name, overrides).getKey();
467
468
469 ServiceDescriptor sd = (ServiceDescriptor) registry.lookupObject(key);
470
471 synchronized (this)
472 {
473 if (sd == null)
474 {
475 sd = createServiceDescriptor(type, name, overrides);
476 try
477 {
478 registry.registerObject(key, sd, ServiceDescriptor.class);
479 }
480 catch (RegistrationException e)
481 {
482 throw new ServiceException(e.getI18nMessage(), e);
483 }
484 }
485 }
486 return sd;
487 }
488
489 protected ServiceDescriptor createServiceDescriptor(ServiceType type, String name, Properties overrides) throws ServiceException
490 {
491
492 String scheme = name;
493 if (name.contains(":"))
494 {
495 scheme = name.substring(0, name.indexOf(":"));
496 }
497
498 Properties props = SpiUtils.findServiceDescriptor(type, scheme);
499 if (props == null)
500 {
501 throw new ServiceException(CoreMessages.failedToLoad(type + " " + scheme));
502 }
503
504 return ServiceDescriptorFactory.create(type, name, props, overrides, muleContext,
505 muleContext.getExecutionClassLoader());
506 }
507
508
509
510
511 public void registerAgent(Agent agent) throws MuleException
512 {
513 registry.registerObject(getName(agent), agent, Agent.class);
514 }
515
516
517
518
519 public void registerConnector(Connector connector) throws MuleException
520 {
521 registry.registerObject(getName(connector), connector, Connector.class);
522 }
523
524
525
526
527 public void registerEndpoint(ImmutableEndpoint endpoint) throws MuleException
528 {
529 registry.registerObject(getName(endpoint), endpoint, ImmutableEndpoint.class);
530 }
531
532
533
534
535 public void registerEndpointBuilder(String name, EndpointBuilder builder) throws MuleException
536 {
537 registry.registerObject(name, builder, EndpointBuilder.class);
538 }
539
540
541
542
543 public void registerModel(Model model) throws MuleException
544 {
545 registry.registerObject(getName(model), model, Model.class);
546 }
547
548
549
550
551 public void registerService(Service service) throws MuleException
552 {
553 registry.registerObject(getName(service), service, Service.class);
554 }
555
556
557
558
559 public void unregisterService(String serviceName) throws MuleException
560 {
561 registry.unregisterObject(serviceName, Service.class);
562 }
563
564
565
566
567 public void registerFlowConstruct(FlowConstruct flowConstruct) throws MuleException
568 {
569 registry.registerObject(getName(flowConstruct), flowConstruct, FlowConstruct.class);
570 }
571
572
573
574
575 public void unregisterFlowConstruct(String flowConstructName) throws MuleException
576 {
577 registry.unregisterObject(flowConstructName, FlowConstruct.class);
578 }
579
580
581
582
583 public void unregisterAgent(String agentName) throws MuleException
584 {
585 registry.unregisterObject(agentName, Agent.class);
586 }
587
588
589
590
591 public void unregisterConnector(String connectorName) throws MuleException
592 {
593 registry.unregisterObject(connectorName, Connector.class);
594 }
595
596
597
598
599 public void unregisterEndpoint(String endpointName) throws MuleException
600 {
601 registry.unregisterObject(endpointName, ImmutableEndpoint.class);
602 }
603
604
605
606
607 public void unregisterModel(String modelName) throws MuleException
608 {
609 registry.unregisterObject(modelName, Model.class);
610 }
611
612
613
614
615 public void unregisterTransformer(String transformerName) throws MuleException
616 {
617 Transformer transformer = lookupTransformer(transformerName);
618 notifyTransformerResolvers(transformer, TransformerResolver.RegistryAction.REMOVED);
619 registry.unregisterObject(transformerName, Transformer.class);
620
621 }
622
623
624
625
626 public Object applyProcessorsAndLifecycle(Object object) throws MuleException
627 {
628 object = applyProcessors(object);
629 object = applyLifecycle(object);
630 return object;
631 }
632
633
634
635
636 public Object applyProcessors(Object object) throws MuleException
637 {
638 return registry.getTransientRegistry().applyProcessors(object, null);
639 }
640
641
642
643
644 public Object applyProcessors(Object object, int flags) throws MuleException
645 {
646 return registry.getTransientRegistry().applyProcessors(object, flags);
647 }
648
649
650
651
652 public Object applyLifecycle(Object object) throws MuleException
653 {
654 return registry.getTransientRegistry().applyLifecycle(object);
655 }
656
657 public Object applyLifecycle(Object object, String phase) throws MuleException
658 {
659 return registry.getTransientRegistry().applyLifecycle(object, phase);
660 }
661
662
663
664
665
666
667
668
669 public <T> T lookupObject(Class<T> type) throws RegistrationException
670 {
671 return registry.lookupObject(type);
672 }
673
674 @SuppressWarnings("unchecked")
675 public <T> T lookupObject(String key)
676 {
677 return (T) registry.lookupObject(key);
678 }
679
680
681
682
683 public <T> Collection<T> lookupObjects(Class<T> type)
684 {
685 return registry.lookupObjects(type);
686 }
687
688
689
690
691 public <T> Collection<T> lookupObjectsForLifecycle(Class<T> type)
692 {
693 return registry.lookupObjectsForLifecycle(type);
694 }
695
696 @SuppressWarnings("unchecked")
697 public <T> T get(String key)
698 {
699 return (T)registry.get(key);
700 }
701
702 public <T> Map<String, T> lookupByType(Class<T> type)
703 {
704 return registry.lookupByType(type);
705 }
706
707
708
709
710 public void registerObject(String key, Object value, Object metadata) throws RegistrationException
711 {
712 registry.registerObject(key, value, metadata);
713 }
714
715
716
717
718 public void registerObject(String key, Object value) throws RegistrationException
719 {
720 registry.registerObject(key, value);
721 }
722
723
724
725
726 public void registerObjects(Map objects) throws RegistrationException
727 {
728 registry.registerObjects(objects);
729 }
730
731
732
733
734 public void unregisterObject(String key, Object metadata) throws RegistrationException
735 {
736 registry.unregisterObject(key, metadata);
737 }
738
739
740
741
742 public void unregisterObject(String key) throws RegistrationException
743 {
744 registry.unregisterObject(key);
745 }
746
747
748
749
750
751
752
753
754 protected String getName(Object obj)
755 {
756 String name = null;
757 if (obj instanceof NameableObject)
758 {
759 name = ((NameableObject) obj).getName();
760 }
761 else if (obj instanceof FlowConstruct)
762 {
763 name = ((FlowConstruct) obj).getName();
764 }
765 if (StringUtils.isBlank(name))
766 {
767 name = obj.getClass().getName() + ":" + UUID.getUUID();
768 }
769 return name;
770 }
771
772
773
774
775
776
777
778
779 public String getRegistryId()
780 {
781 return this.toString();
782 }
783
784
785
786
787 public boolean isReadOnly()
788 {
789 return false;
790 }
791
792
793
794
795 public boolean isRemote()
796 {
797 return false;
798 }
799
800 private String getDataTypeSourceResultPairHash(DataType<?> source, DataType<?> result)
801 {
802 return source.getClass().getName() + source.hashCode() + ":" + result.getClass().getName()
803 + result.hashCode();
804 }
805
806 private class TransformerResolverComparator implements Comparator<TransformerResolver>
807 {
808 public int compare(TransformerResolver transformerResolver, TransformerResolver transformerResolver1)
809 {
810 if (transformerResolver.getClass().equals(TypeBasedTransformerResolver.class))
811 {
812 return 1;
813 }
814
815 if (transformerResolver1.getClass().equals(TypeBasedTransformerResolver.class))
816 {
817 return -1;
818 }
819 return 0;
820 }
821 }
822 }
823
824