1 package com.atlassian.event.internal;
2
3 import com.atlassian.event.spi.EventDispatcher;
4 import com.atlassian.event.spi.EventExecutorFactory;
5 import com.atlassian.event.spi.EventRunnableFactory;
6 import com.atlassian.event.spi.ListenerInvoker;
7 import com.google.common.util.concurrent.MoreExecutors;
8 import org.slf4j.Logger;
9 import org.slf4j.LoggerFactory;
10
11 import java.util.concurrent.Executor;
12
13 import static com.google.common.base.Preconditions.checkNotNull;
14
15
16
17
18
19
20
21
22 public class AsynchronousAbleEventDispatcher implements EventDispatcher {
23 private static final Logger log = LoggerFactory.getLogger(AsynchronousAbleEventDispatcher.class);
24
25
26
27
28 private static final Executor SYNCHRONOUS_EXECUTOR = MoreExecutors.directExecutor();
29
30
31
32
33 private static final EventRunnableFactory SIMPLE_RUNNABLE_FACTORY = new EventRunnableFactory() {
34 public Runnable getRunnable(final ListenerInvoker invoker, final Object event) {
35 return new Runnable() {
36 public void run() {
37 try {
38 invoker.invoke(event);
39 } catch (Exception e) {
40
41
42 if (log.isErrorEnabled()) {
43 log.error("There was an exception thrown trying to dispatch event [" + event + "] from the invoker [" + invoker + "]", e);
44 }
45 }
46 }
47 };
48 }
49 };
50
51
52
53
54 private final Executor asynchronousExecutor;
55
56 private final AsynchronousEventResolver asynchronousEventResolver;
57
58 private final EventRunnableFactory runnableFactory;
59
60 public AsynchronousAbleEventDispatcher(Executor executor, AsynchronousEventResolver asynchronousEventResolver, EventRunnableFactory runnableFactory) {
61 this.asynchronousEventResolver = checkNotNull(asynchronousEventResolver);
62 this.asynchronousExecutor = checkNotNull(executor);
63 this.runnableFactory = checkNotNull(runnableFactory);
64 }
65
66
67 public AsynchronousAbleEventDispatcher(Executor executor, AsynchronousEventResolver asynchronousEventResolver) {
68 this(executor, asynchronousEventResolver, SIMPLE_RUNNABLE_FACTORY);
69 }
70
71
72 public AsynchronousAbleEventDispatcher(EventExecutorFactory executorFactory, AsynchronousEventResolver asynchronousEventResolver, EventRunnableFactory runnableFactory) {
73 this(checkNotNull(executorFactory).getExecutor(), asynchronousEventResolver, runnableFactory);
74 }
75
76
77 public AsynchronousAbleEventDispatcher(EventExecutorFactory executorFactory, AsynchronousEventResolver asynchronousEventResolver) {
78 this(executorFactory, asynchronousEventResolver, SIMPLE_RUNNABLE_FACTORY);
79 }
80
81
82 public AsynchronousAbleEventDispatcher(EventExecutorFactory executorFactory) {
83 this(executorFactory, new AnnotationAsynchronousEventResolver(), SIMPLE_RUNNABLE_FACTORY);
84 }
85
86
87 public void dispatch(final ListenerInvoker invoker, final Object event) {
88 executorFor(checkNotNull(invoker), checkNotNull(event)).execute(runnableFactory.getRunnable(invoker, event));
89 }
90
91 protected Executor executorFor(ListenerInvoker invoker, Object event) {
92 return asynchronousEventResolver.isAsynchronousEvent(event) && invoker.supportAsynchronousEvents()
93 ? getAsynchronousExecutor()
94 : getSynchronousExecutor();
95 }
96
97 protected Executor getSynchronousExecutor() {
98 return SYNCHRONOUS_EXECUTOR;
99 }
100
101 protected Executor getAsynchronousExecutor() {
102 return asynchronousExecutor;
103 }
104
105 }