1
2
3
4
5
6
7
8
9
10
11 package org.mule.impl.model;
12
13 import org.mule.MuleManager;
14 import org.mule.config.i18n.CoreMessages;
15 import org.mule.config.i18n.MessageFactory;
16 import org.mule.impl.DefaultComponentExceptionStrategy;
17 import org.mule.impl.MuleDescriptor;
18 import org.mule.impl.OptimizedRequestContext;
19 import org.mule.impl.internal.notifications.ComponentNotification;
20 import org.mule.management.stats.ComponentStatistics;
21 import org.mule.providers.AbstractConnector;
22 import org.mule.umo.ComponentException;
23 import org.mule.umo.UMOComponent;
24 import org.mule.umo.UMODescriptor;
25 import org.mule.umo.UMOEvent;
26 import org.mule.umo.UMOException;
27 import org.mule.umo.UMOMessage;
28 import org.mule.umo.endpoint.UMOEndpoint;
29 import org.mule.umo.endpoint.UMOImmutableEndpoint;
30 import org.mule.umo.lifecycle.InitialisationException;
31 import org.mule.umo.model.ModelException;
32 import org.mule.umo.model.UMOModel;
33 import org.mule.umo.provider.DispatchException;
34 import org.mule.umo.provider.UMOMessageReceiver;
35 import org.mule.util.concurrent.WaitableBoolean;
36
37 import java.beans.ExceptionListener;
38 import java.util.ArrayList;
39 import java.util.Iterator;
40 import java.util.List;
41
42 import edu.emory.mathcs.backport.java.util.concurrent.atomic.AtomicBoolean;
43
44 import org.apache.commons.logging.Log;
45 import org.apache.commons.logging.LogFactory;
46
47
48
49
50 public abstract class AbstractComponent implements UMOComponent
51 {
52
53
54
55 protected transient Log logger = LogFactory.getLog(getClass());
56
57
58
59
60 protected MuleDescriptor descriptor = null;
61
62 protected ComponentStatistics stats = null;
63
64
65
66
67 protected AtomicBoolean stopped = new AtomicBoolean(true);
68
69
70
71
72 protected WaitableBoolean stopping = new WaitableBoolean(false);
73
74
75
76
77 protected AtomicBoolean poolInitialised = new AtomicBoolean(false);
78
79
80
81
82
83 protected ExceptionListener exceptionListener = null;
84
85
86
87
88 protected AtomicBoolean initialised = new AtomicBoolean(false);
89
90
91
92
93 protected UMOModel model;
94
95
96
97
98 protected WaitableBoolean paused = new WaitableBoolean(false);
99
100
101
102
103 public AbstractComponent(MuleDescriptor descriptor, UMOModel model)
104 {
105 if (descriptor == null)
106 {
107 throw new IllegalArgumentException("Descriptor cannot be null");
108 }
109 this.descriptor = descriptor;
110 this.model = model;
111 }
112
113
114
115
116
117
118
119
120
121
122 public final synchronized void initialise() throws InitialisationException
123 {
124 if (initialised.get())
125 {
126 throw new InitialisationException(
127 CoreMessages.objectAlreadyInitialised("Component '" + descriptor.getName() + "'"), this);
128 }
129 descriptor.initialise();
130
131 this.exceptionListener = descriptor.getExceptionListener();
132
133
134 stats = createStatistics();
135
136 stats.setEnabled(((MuleManager) MuleManager.getInstance()).getStatistics().isEnabled());
137 ((MuleManager) MuleManager.getInstance()).getStatistics().add(stats);
138 stats.setOutboundRouterStat(getDescriptor().getOutboundRouter().getStatistics());
139 stats.setInboundRouterStat(getDescriptor().getInboundRouter().getStatistics());
140
141 doInitialise();
142 initialised.set(true);
143 fireComponentNotification(ComponentNotification.COMPONENT_INITIALISED);
144
145 }
146
147 protected ComponentStatistics createStatistics()
148 {
149 return new ComponentStatistics(getName(),
150 descriptor.getThreadingProfile().getMaxThreadsActive());
151 }
152
153 protected void fireComponentNotification(int action)
154 {
155 MuleManager.getInstance().fireNotification(new ComponentNotification(descriptor, action));
156 }
157
158 public void forceStop() throws UMOException
159 {
160 if (!stopped.get())
161 {
162 logger.debug("Stopping UMOComponent");
163 stopping.set(true);
164 fireComponentNotification(ComponentNotification.COMPONENT_STOPPING);
165 doForceStop();
166 stopped.set(true);
167 stopping.set(false);
168 fireComponentNotification(ComponentNotification.COMPONENT_STOPPED);
169 }
170 }
171
172 public void stop() throws UMOException
173 {
174 if (!stopped.get())
175 {
176 logger.debug("Stopping UMOComponent");
177 stopping.set(true);
178 fireComponentNotification(ComponentNotification.COMPONENT_STOPPING);
179
180
181 unregisterListeners();
182
183 doStop();
184 stopped.set(true);
185 initialised.set(false);
186 fireComponentNotification(ComponentNotification.COMPONENT_STOPPED);
187 }
188 }
189
190 public void start() throws UMOException
191 {
192 start(false);
193 }
194
195
196
197
198
199
200
201 protected void start(boolean startPaused) throws UMOException
202 {
203
204
205 registerListeners();
206
207
208
209
210
211
212
213 connectListeners();
214
215
216 if (stopped.get())
217 {
218 stopped.set(false);
219 paused.set(false);
220 doStart();
221 }
222 fireComponentNotification(ComponentNotification.COMPONENT_STARTED);
223 if (startPaused)
224 {
225 pause();
226 }
227
228
229
230
231
232 startListeners();
233 }
234
235
236
237
238
239
240 public final void pause() throws UMOException
241 {
242
243 doPause();
244 paused.set(true);
245 fireComponentNotification(ComponentNotification.COMPONENT_PAUSED);
246 }
247
248
249
250
251
252 public final void resume() throws UMOException
253 {
254 doResume();
255 paused.set(false);
256 fireComponentNotification(ComponentNotification.COMPONENT_RESUMED);
257 }
258
259
260
261
262
263
264 public boolean isPaused()
265 {
266 return paused.get();
267 }
268
269
270
271
272
273
274
275
276 protected void doPause() throws UMOException
277 {
278
279 }
280
281
282
283
284
285
286
287
288 protected void doResume() throws UMOException
289 {
290
291 }
292
293 public final void dispose()
294 {
295 try
296 {
297 if (!stopped.get())
298 {
299 stop();
300 }
301 }
302 catch (UMOException e)
303 {
304
305
306 logger.error("Failed to stop component: " + descriptor.getName(), e);
307 }
308 doDispose();
309 fireComponentNotification(ComponentNotification.COMPONENT_DISPOSED);
310 ((MuleManager) MuleManager.getInstance()).getStatistics().remove(stats);
311 }
312
313 public ComponentStatistics getStatistics()
314 {
315 return stats;
316 }
317
318
319
320
321
322
323 public UMODescriptor getDescriptor()
324 {
325 return descriptor;
326 }
327
328 public void dispatchEvent(UMOEvent event) throws UMOException
329 {
330 if (stopping.get() || stopped.get())
331 {
332 throw new ComponentException(
333 CoreMessages.componentIsStopped(this.getDescriptor().getName()),
334 event.getMessage(), this);
335 }
336
337 try
338 {
339 waitIfPaused(event);
340 }
341 catch (InterruptedException e)
342 {
343 throw new ComponentException(event.getMessage(), this, e);
344 }
345
346
347
348 UMOImmutableEndpoint endpoint = event.getEndpoint();
349
350 if (!endpoint.canReceive())
351 {
352 try
353 {
354 endpoint.dispatch(event);
355 }
356 catch (Exception e)
357 {
358 throw new DispatchException(event.getMessage(), event.getEndpoint(), e);
359 }
360
361 return;
362 }
363
364
365 if (stats.isEnabled())
366 {
367 stats.incReceivedEventASync();
368 }
369
370 if (logger.isDebugEnabled())
371 {
372 logger.debug("Component: " + descriptor.getName() + " has received asynchronous event on: "
373 + event.getEndpoint().getEndpointURI());
374 }
375
376 doDispatch(event);
377 }
378
379 public UMOMessage sendEvent(UMOEvent event) throws UMOException
380 {
381 if (stopping.get() || stopped.get())
382 {
383 throw new ComponentException(
384 CoreMessages.componentIsStopped(this.getDescriptor().getName()),
385 event.getMessage(), this);
386 }
387
388 try
389 {
390 waitIfPaused(event);
391 }
392 catch (InterruptedException e)
393 {
394 throw new ComponentException(event.getMessage(), this, e);
395 }
396
397 if (stats.isEnabled())
398 {
399 stats.incReceivedEventSync();
400 }
401 if (logger.isDebugEnabled())
402 {
403 logger.debug("Component: " + descriptor.getName() + " has received synchronous event on: "
404 + event.getEndpoint().getEndpointURI());
405 }
406 event = OptimizedRequestContext.unsafeSetEvent(event);
407 return doSend(event);
408 }
409
410
411
412
413
414
415
416
417
418 protected void waitIfPaused(UMOEvent event) throws InterruptedException
419 {
420 if (logger.isDebugEnabled() && paused.get())
421 {
422 logger.debug("Component: " + descriptor.getName()
423 + " is paused. Blocking call until resume is called");
424 }
425 paused.whenFalse(null);
426 }
427
428
429
430
431 public String getName()
432 {
433 return descriptor.getName();
434 }
435
436
437
438
439
440
441 public String toString()
442 {
443 return descriptor.getName();
444 }
445
446 public boolean isStopped()
447 {
448 return stopped.get();
449 }
450
451 public boolean isStopping()
452 {
453 return stopping.get();
454 }
455
456 protected void handleException(Exception e)
457 {
458 if (exceptionListener instanceof DefaultComponentExceptionStrategy)
459 {
460 if (((DefaultComponentExceptionStrategy) exceptionListener).getComponent() == null)
461 {
462 ((DefaultComponentExceptionStrategy) exceptionListener).setComponent(this);
463 }
464 }
465 exceptionListener.exceptionThrown(e);
466 }
467
468
469
470
471
472
473
474 protected Object lookupComponent() throws UMOException
475 {
476 return ComponentFactory.createComponent(getDescriptor());
477 }
478
479 protected void doForceStop() throws UMOException
480 {
481
482 }
483
484 protected void doStop() throws UMOException
485 {
486
487 }
488
489 protected void doStart() throws UMOException
490 {
491
492 }
493
494 protected void doDispose()
495 {
496
497 }
498
499 protected void doInitialise() throws InitialisationException
500 {
501
502 }
503
504 public boolean isStarted()
505 {
506 return !stopped.get();
507 }
508
509 protected abstract UMOMessage doSend(UMOEvent event) throws UMOException;
510
511 protected abstract void doDispatch(UMOEvent event) throws UMOException;
512
513 public Object getInstance() throws UMOException
514 {
515 return lookupComponent();
516 }
517
518 protected void registerListeners() throws UMOException
519 {
520 UMOEndpoint endpoint;
521 List endpoints = getIncomingEndpoints();
522
523 for (Iterator it = endpoints.iterator(); it.hasNext();)
524 {
525 endpoint = (UMOEndpoint) it.next();
526 try
527 {
528 endpoint.getConnector().registerListener(this, endpoint);
529 }
530 catch (UMOException e)
531 {
532 throw e;
533 }
534 catch (Exception e)
535 {
536 throw new ModelException(
537 CoreMessages.failedtoRegisterOnEndpoint(this.getDescriptor().getName(),
538 endpoint.getEndpointURI()), e);
539 }
540 }
541 }
542
543 protected void unregisterListeners() throws UMOException
544 {
545 UMOEndpoint endpoint;
546 List endpoints = getIncomingEndpoints();
547
548 for (Iterator it = endpoints.iterator(); it.hasNext();)
549 {
550 endpoint = (UMOEndpoint) it.next();
551 try
552 {
553 endpoint.getConnector().unregisterListener(this, endpoint);
554 }
555 catch (UMOException e)
556 {
557 throw e;
558 }
559 catch (Exception e)
560 {
561 throw new ModelException(
562 CoreMessages.failedToUnregister(this.getDescriptor().getName(),
563 endpoint.getEndpointURI()), e);
564 }
565 }
566 }
567
568 protected void startListeners() throws UMOException
569 {
570 UMOEndpoint endpoint;
571 List endpoints = getIncomingEndpoints();
572
573 for (Iterator it = endpoints.iterator(); it.hasNext();)
574 {
575 endpoint = (UMOEndpoint) it.next();
576 UMOMessageReceiver receiver = ((AbstractConnector) endpoint.getConnector()).getReceiver(this,
577 endpoint);
578 if (receiver != null && endpoint.getConnector().isStarted()
579 && endpoint.getInitialState().equals(UMOEndpoint.INITIAL_STATE_STARTED))
580 {
581 receiver.start();
582 }
583 }
584 }
585
586 protected void stopListeners() throws UMOException
587 {
588 UMOEndpoint endpoint;
589 List endpoints = getIncomingEndpoints();
590
591 for (Iterator it = endpoints.iterator(); it.hasNext();)
592 {
593 endpoint = (UMOEndpoint) it.next();
594 UMOMessageReceiver receiver = ((AbstractConnector) endpoint.getConnector()).getReceiver(this,
595 endpoint);
596 if (receiver != null)
597 {
598 receiver.stop();
599 }
600 }
601 }
602
603 protected void connectListeners() throws UMOException
604 {
605 UMOEndpoint endpoint;
606 List endpoints = getIncomingEndpoints();
607
608 for (Iterator it = endpoints.iterator(); it.hasNext();)
609 {
610 endpoint = (UMOEndpoint) it.next();
611 UMOMessageReceiver receiver = ((AbstractConnector) endpoint.getConnector()).getReceiver(this,
612 endpoint);
613 if (receiver != null)
614 {
615 try
616 {
617 receiver.connect();
618 }
619 catch (Exception e)
620 {
621 throw new ModelException(
622 MessageFactory.createStaticMessage("Failed to connect listener "
623 + receiver + " for endpoint " + endpoint.getName()),
624 e);
625 }
626 }
627 }
628 }
629
630 protected void disconnectListeners() throws UMOException
631 {
632 UMOEndpoint endpoint;
633 List endpoints = getIncomingEndpoints();
634
635 for (Iterator it = endpoints.iterator(); it.hasNext();)
636 {
637 endpoint = (UMOEndpoint) it.next();
638 UMOMessageReceiver receiver = ((AbstractConnector) endpoint.getConnector()).getReceiver(this,
639 endpoint);
640 if (receiver != null)
641 {
642 try
643 {
644 receiver.disconnect();
645 }
646 catch (Exception e)
647 {
648 throw new ModelException(
649 MessageFactory.createStaticMessage("Failed to disconnect listener "
650 + receiver + " for endpoint " + endpoint.getName()),
651 e);
652 }
653 }
654 }
655 }
656
657
658
659
660 protected List getIncomingEndpoints()
661 {
662 List endpoints = new ArrayList();
663
664
665 endpoints.addAll(getDescriptor().getInboundRouter().getEndpoints());
666
667 if (getDescriptor().getInboundEndpoint() != null)
668 {
669 endpoints.add(getDescriptor().getInboundEndpoint());
670 }
671
672
673 if (getDescriptor().getResponseRouter() != null
674 && getDescriptor().getResponseRouter().getEndpoints() != null)
675 {
676 endpoints.addAll(getDescriptor().getResponseRouter().getEndpoints());
677 }
678 return endpoints;
679 }
680
681 }