View Javadoc
1   package com.atlassian.plugin.event.impl;
2   
3   import com.atlassian.event.api.EventListener;
4   import com.atlassian.event.api.EventPublisher;
5   import com.atlassian.plugin.event.PluginEventListener;
6   import org.junit.After;
7   import org.junit.Before;
8   import org.junit.Test;
9   import org.junit.runner.RunWith;
10  import org.mockito.Mock;
11  import org.mockito.runners.MockitoJUnitRunner;
12  
13  import java.lang.reflect.Method;
14  
15  import static org.hamcrest.core.IsNull.notNullValue;
16  import static org.junit.Assert.assertEquals;
17  import static org.junit.Assert.assertThat;
18  import static org.junit.Assert.fail;
19  import static org.mockito.Matchers.anyObject;
20  import static org.mockito.Matchers.anyString;
21  import static org.mockito.Mockito.mock;
22  import static org.mockito.Mockito.never;
23  import static org.mockito.Mockito.times;
24  import static org.mockito.Mockito.verify;
25  
26  @RunWith(MockitoJUnitRunner.class)
27  public class TestDefaultPluginEventManager {
28      private final Object someObject = new Object();
29      private final String someString = "string";
30  
31      @Mock
32      private MethodTestListener methodTestListener;
33  
34      private DefaultPluginEventManager defaultPluginEventManager;
35  
36      @Before
37      public void createDefaultPluginEventManager() {
38          defaultPluginEventManager = new DefaultPluginEventManager();
39          assertThat(defaultPluginEventManager.getEventPublisher(), notNullValue(EventPublisher.class));
40      }
41  
42      @After
43      public void discardDefaultPluginEventManager() {
44          defaultPluginEventManager = null;
45      }
46  
47      @Test
48      public void broadcastCallsListenerChannelForType() {
49          defaultPluginEventManager.register(methodTestListener);
50          defaultPluginEventManager.broadcast(someObject);
51          verify(methodTestListener).channel(someObject);
52          verify(methodTestListener, never()).channel(anyString());
53      }
54  
55      @Test
56      public void broadcastCallsListenerChannelForSupertype() {
57          final Integer someInteger = 0;
58          defaultPluginEventManager.register(methodTestListener);
59          defaultPluginEventManager.broadcast(someInteger);
60          verify(methodTestListener).channel(someInteger);
61          verify(methodTestListener, never()).channel(anyString());
62      }
63  
64      @Test
65      public void broadcastCallsListenerChannelForTypeAndSupertype() {
66          defaultPluginEventManager.register(methodTestListener);
67          defaultPluginEventManager.broadcast(someString);
68          // The cast ensures we verify both overloads are called
69          verify(methodTestListener).channel((Object) someString);
70          verify(methodTestListener).channel(someString);
71      }
72  
73      @Test
74      public void listenerCalledOnceEvenIfRegisteredTwice() {
75          defaultPluginEventManager.register(methodTestListener);
76          defaultPluginEventManager.register(methodTestListener);
77          defaultPluginEventManager.broadcast(someObject);
78          verify(methodTestListener).channel(someObject);
79          verify(methodTestListener, never()).channel(anyString());
80      }
81  
82      @Test
83      public void registerUnmatchingListenerThrows() {
84          BadListener badListener = mock(BadListener.class);
85          try {
86              defaultPluginEventManager.register(badListener);
87              fail();
88          } catch (IllegalArgumentException ex) {
89              // test passed
90          }
91          verify(badListener, never()).someMethod();
92      }
93  
94      @Test
95      public void customSelectorMatchesAndOverridesDefault() {
96          ListenerMethodSelector onEventSelector = new ListenerMethodSelector() {
97              public boolean isListenerMethod(Method method) {
98                  return "onEvent".equals(method.getName());
99              }
100         };
101         defaultPluginEventManager = new DefaultPluginEventManager(onEventSelector);
102         defaultPluginEventManager.register(methodTestListener);
103         defaultPluginEventManager.broadcast(someString);
104         verify(methodTestListener).onEvent(someString);
105         verify(methodTestListener, never()).channel(anyObject());
106         verify(methodTestListener, never()).channel(anyString());
107     }
108 
109     @Test
110     public void overlappingSelectorsBothMatch() {
111         ListenerMethodSelector firstSelector = new MethodNameListenerMethodSelector();
112         ListenerMethodSelector secondSelector = new MethodNameListenerMethodSelector();
113         defaultPluginEventManager = new DefaultPluginEventManager(firstSelector, secondSelector);
114         defaultPluginEventManager.register(methodTestListener);
115         defaultPluginEventManager.broadcast(someObject);
116         verify(methodTestListener, times(2)).channel(someObject);
117     }
118 
119     @Test
120     public void broadcastCallsAnnotatedMethods() {
121         // I don't believe this can be done with mocks, because the stub
122         // is not annotated, and i don't see a way of getting it annotated.
123         AnnotationTestListener listener = new AnnotationTestListener();
124         defaultPluginEventManager.register(listener);
125         defaultPluginEventManager.broadcast(someObject);
126         assertEquals(1, listener.eventListenerCalled);
127         assertEquals(1, listener.pluginEventListenerCalled);
128     }
129 
130     @Test
131     public void unregisterStopsBroadcastSendingEvents() {
132         defaultPluginEventManager.register(methodTestListener);
133         defaultPluginEventManager.broadcast(someObject);
134         verify(methodTestListener).channel(someObject);
135         defaultPluginEventManager.unregister(methodTestListener);
136         defaultPluginEventManager.broadcast(someObject);
137         // This checks it was called once, i.e. first broadcast
138         verify(methodTestListener).channel(someObject);
139     }
140 
141     @Test(expected = IllegalArgumentException.class)
142     public void registerNullThrows() {
143         defaultPluginEventManager.register(null);
144     }
145 
146     @Test(expected = IllegalArgumentException.class)
147     public void unregisterNullThrows() {
148         defaultPluginEventManager.unregister(null);
149     }
150 
151     public static class AnnotationTestListener {
152         int pluginEventListenerCalled = 0;
153         int eventListenerCalled = 0;
154 
155         @PluginEventListener
156         public void doEventOld(Object obj) {
157             ++pluginEventListenerCalled;
158         }
159 
160         @EventListener
161         public void doEventNew(Object obj) {
162             ++eventListenerCalled;
163         }
164     }
165 
166     public static class MethodTestListener {
167         public void channel(Object object) {
168         }
169 
170         public void channel(String string) {
171         }
172 
173         public void onEvent(String string) {
174         }
175     }
176 
177     public static class BadListener {
178         public void someMethod() {
179         }
180     }
181 }