1 package com.atlassian.event.spring;
2
3 import com.atlassian.event.api.EventListenerRegistrar;
4 import com.atlassian.event.config.ListenerHandlersConfiguration;
5 import com.atlassian.event.spi.ListenerHandler;
6 import com.atlassian.event.spi.ListenerInvoker;
7 import com.atlassian.plugin.ModuleDescriptor;
8 import com.atlassian.plugin.Plugin;
9 import com.atlassian.plugin.event.events.PluginModuleEnabledEvent;
10 import org.junit.Before;
11 import org.junit.Test;
12 import org.junit.runner.RunWith;
13 import org.mockito.Mock;
14 import org.mockito.runners.MockitoJUnitRunner;
15 import org.springframework.beans.factory.NoSuchBeanDefinitionException;
16 import org.springframework.beans.factory.config.BeanDefinition;
17 import org.springframework.beans.factory.config.ConfigurableBeanFactory;
18 import org.springframework.test.util.ReflectionTestUtils;
19
20 import java.util.Collection;
21 import java.util.List;
22 import java.util.Map;
23
24 import static java.util.Collections.EMPTY_LIST;
25 import static java.util.Collections.singletonList;
26 import static org.hamcrest.MatcherAssert.assertThat;
27 import static org.hamcrest.Matchers.is;
28 import static org.hamcrest.collection.IsCollectionWithSize.hasSize;
29 import static org.hamcrest.core.IsCollectionContaining.hasItem;
30 import static org.mockito.Matchers.isA;
31 import static org.mockito.Mockito.verify;
32 import static org.mockito.Mockito.verifyNoMoreInteractions;
33 import static org.mockito.Mockito.when;
34
35 @RunWith(MockitoJUnitRunner.class)
36 public class EventListenerRegistrarBeanProcessorTest {
37 private static final String REGISTRAR_BEAN_NAME = "registrar";
38
39 private EventListenerRegistrarBeanProcessor registrarBeanProcessor;
40
41 @Mock
42 private ListenerHandlersConfiguration listenerHandlersConfiguration;
43
44 @Mock
45 private EventListenerRegistrar eventListenerRegistrar;
46
47 @Mock
48 private ConfigurableBeanFactory beanFactory;
49
50 @Mock
51 private BeanDefinition beanDefinition;
52
53 @Mock
54 private ListenerHandler listenerHandler;
55
56 @Mock
57 private ListenerInvoker listenerInvoker;
58
59 @Mock
60 private ModuleDescriptor moduleDescriptor;
61
62 @Mock
63 private Plugin plugin;
64
65 private PluginModuleEnabledEvent pluginModuleEnabledEvent;
66
67 private final SomeListenerClass listenerBean = new SomeListenerClass();
68
69 @Before
70 public void setup() {
71 registrarBeanProcessor = new EventListenerRegistrarBeanProcessor(REGISTRAR_BEAN_NAME, listenerHandlersConfiguration);
72
73
74
75
76 registrarBeanProcessor.setBeanFactory(beanFactory);
77 when(beanFactory.getMergedBeanDefinition(isA(String.class))).thenReturn(beanDefinition);
78 when(beanFactory.getMergedBeanDefinition(null)).thenThrow(new NoSuchBeanDefinitionException("null bean name"));
79 when(beanDefinition.isSingleton()).thenReturn(true);
80
81
82 when(listenerHandlersConfiguration.getListenerHandlers()).thenReturn(singletonList(listenerHandler));
83
84
85 List listenerInvokers = singletonList(listenerInvoker);
86 when(listenerHandler.getInvokers(listenerBean)).thenReturn(listenerInvokers);
87
88 when(moduleDescriptor.getPlugin()).thenReturn(plugin);
89 when(moduleDescriptor.getModuleClass()).thenReturn(Object.class);
90 when(moduleDescriptor.getModule()).thenReturn(listenerBean);
91 when(plugin.getKey()).thenReturn("com.atlassian.test:some.plugin");
92
93 pluginModuleEnabledEvent = new PluginModuleEnabledEvent(moduleDescriptor);
94 }
95
96 @Test
97 public void testThatTheListenerIsRegisteredImmediatelyIfTheRegistrarIsAvailable() {
98 processTheRegistrarProcessorBean();
99 processTheListenerBean();
100
101 verifyThatTheListenerHasBeenRegistered();
102 verifyThatNoMoreListenersNeedToBeRegistered();
103 }
104
105 @Test
106 public void testThatTheListenerIsRememberedForLaterRegistrationIfTheRegistrarIsNotAvailable() {
107 processTheListenerBean();
108
109 verifyNoMoreInteractions(eventListenerRegistrar);
110 assertThat(listenersToBeRegistered(), hasItem(listenerBean));
111
112 processTheRegistrarProcessorBean();
113
114 verifyThatTheListenerHasBeenRegistered();
115 verifyThatNoMoreListenersNeedToBeRegistered();
116 }
117
118 @Test
119 public void testThatNonListenerBeansAreIgnored() {
120 when(listenerHandler.getInvokers(listenerBean)).thenReturn(EMPTY_LIST);
121 processTheRegistrarProcessorBean();
122 processTheListenerBean();
123
124 verifyNoMoreInteractions(eventListenerRegistrar);
125 verifyThatNoMoreListenersNeedToBeRegistered();
126 }
127
128 @Test
129 public void blacklistedPluginsAreNotRegistered() {
130 when(plugin.getKey()).thenReturn("com.atlassian.activeobjects.activeobjects-plugin");
131
132 registrarBeanProcessor.onPluginModuleEnabled(pluginModuleEnabledEvent);
133 verifyThatNoMoreListenersNeedToBeRegistered();
134 }
135
136 @Test
137 public void validListenerModuklesAreRegisteredAsListeners() {
138 registrarBeanProcessor.onPluginModuleEnabled(pluginModuleEnabledEvent);
139 processTheRegistrarProcessorBean();
140 verifyThatTheListenerHasBeenRegistered();
141 }
142
143 private Collection<Object> listenersToBeRegistered() {
144 final Map<String, Object> listenersToBeRegistered =
145 (Map<String, Object>) ReflectionTestUtils.getField(registrarBeanProcessor, "listenersToBeRegistered");
146 return listenersToBeRegistered.values();
147 }
148
149 private void verifyThatNoMoreListenersNeedToBeRegistered() {
150 assertThat(listenersToBeRegistered(), is(hasSize(0)));
151 }
152
153 private void verifyThatTheListenerHasBeenRegistered() {
154 verify(eventListenerRegistrar).register(listenerBean);
155 }
156
157 private void processTheListenerBean() {
158 registrarBeanProcessor.postProcessBeforeInitialization(listenerBean, "listener");
159 }
160
161 private void processTheRegistrarProcessorBean() {
162 registrarBeanProcessor.postProcessAfterInitialization(eventListenerRegistrar, REGISTRAR_BEAN_NAME);
163 }
164
165 private class SomeListenerClass {
166 }
167 }