]> source.dussan.org Git - sonarqube.git/blob
5c789db2d6463dc1ad9a1111992c1569a269a3cb
[sonarqube.git] /
1 /*
2  * SonarQube
3  * Copyright (C) 2009-2023 SonarSource SA
4  * mailto:info AT sonarsource DOT com
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 3 of the License, or (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public License
17  * along with this program; if not, write to the Free Software Foundation,
18  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
19  */
20 package org.sonar.server.project;
21
22 import com.tngtech.java.junit.dataprovider.DataProvider;
23 import com.tngtech.java.junit.dataprovider.DataProviderRunner;
24 import com.tngtech.java.junit.dataprovider.UseDataProvider;
25 import java.util.Collections;
26 import java.util.Random;
27 import java.util.Set;
28 import java.util.stream.Collectors;
29 import java.util.stream.IntStream;
30 import org.junit.Test;
31 import org.junit.runner.RunWith;
32 import org.mockito.InOrder;
33 import org.mockito.Mockito;
34
35 import static java.util.Collections.singleton;
36 import static org.assertj.core.api.Assertions.assertThatCode;
37 import static org.assertj.core.api.Assertions.assertThatThrownBy;
38 import static org.mockito.ArgumentMatchers.any;
39 import static org.mockito.ArgumentMatchers.same;
40 import static org.mockito.Mockito.doThrow;
41 import static org.mockito.Mockito.mock;
42 import static org.mockito.Mockito.verifyNoInteractions;
43 import static org.sonar.db.component.ComponentTesting.newPrivateProjectDto;
44
45 @RunWith(DataProviderRunner.class)
46 public class ProjectLifeCycleListenersImplTest {
47
48   private final ProjectLifeCycleListener listener1 = mock(ProjectLifeCycleListener.class);
49   private final ProjectLifeCycleListener listener2 = mock(ProjectLifeCycleListener.class);
50   private final ProjectLifeCycleListener listener3 = mock(ProjectLifeCycleListener.class);
51   private final ProjectLifeCycleListenersImpl underTestNoListeners = new ProjectLifeCycleListenersImpl();
52   private final ProjectLifeCycleListenersImpl underTestWithListeners = new ProjectLifeCycleListenersImpl(
53     new ProjectLifeCycleListener[] {listener1, listener2, listener3});
54
55   @Test
56   public void onProjectsDeleted_throws_NPE_if_set_is_null() {
57     assertThatThrownBy(() -> underTestWithListeners.onProjectsDeleted(null))
58       .isInstanceOf(NullPointerException.class)
59       .hasMessage("projects can't be null");
60   }
61
62   @Test
63   public void onProjectsDeleted_throws_NPE_if_set_is_null_even_if_no_listeners() {
64     assertThatThrownBy(() -> underTestNoListeners.onProjectsDeleted(null))
65       .isInstanceOf(NullPointerException.class)
66       .hasMessage("projects can't be null");
67   }
68
69   @Test
70   public void onProjectsDeleted_has_no_effect_if_set_is_empty() {
71     underTestNoListeners.onProjectsDeleted(Collections.emptySet());
72
73     underTestWithListeners.onProjectsDeleted(Collections.emptySet());
74     verifyNoInteractions(listener1, listener2, listener3);
75   }
76
77   @Test
78   @UseDataProvider("oneOrManyDeletedProjects")
79   public void onProjectsDeleted_does_not_fail_if_there_is_no_listener(Set<DeletedProject> projects) {
80     assertThatCode(() -> underTestNoListeners.onProjectsDeleted(projects)).doesNotThrowAnyException();
81   }
82
83   @Test
84   @UseDataProvider("oneOrManyDeletedProjects")
85   public void onProjectsDeleted_calls_all_listeners_in_order_of_addition_to_constructor(Set<DeletedProject> projects) {
86     InOrder inOrder = Mockito.inOrder(listener1, listener2, listener3);
87
88     underTestWithListeners.onProjectsDeleted(projects);
89
90     inOrder.verify(listener1).onProjectsDeleted(same(projects));
91     inOrder.verify(listener2).onProjectsDeleted(same(projects));
92     inOrder.verify(listener3).onProjectsDeleted(same(projects));
93     inOrder.verifyNoMoreInteractions();
94   }
95
96   @Test
97   @UseDataProvider("oneOrManyDeletedProjects")
98   public void onProjectsDeleted_calls_all_listeners_even_if_one_throws_an_Exception(Set<DeletedProject> projects) {
99     InOrder inOrder = Mockito.inOrder(listener1, listener2, listener3);
100     doThrow(new RuntimeException("Faking listener2 throwing an exception"))
101       .when(listener2)
102       .onProjectsDeleted(any());
103
104     underTestWithListeners.onProjectsDeleted(projects);
105
106     inOrder.verify(listener1).onProjectsDeleted(same(projects));
107     inOrder.verify(listener2).onProjectsDeleted(same(projects));
108     inOrder.verify(listener3).onProjectsDeleted(same(projects));
109     inOrder.verifyNoMoreInteractions();
110   }
111
112   @Test
113   @UseDataProvider("oneOrManyDeletedProjects")
114   public void onProjectsDeleted_calls_all_listeners_even_if_one_throws_an_Error(Set<DeletedProject> projects) {
115     InOrder inOrder = Mockito.inOrder(listener1, listener2, listener3);
116     doThrow(new Error("Faking listener2 throwing an Error"))
117       .when(listener2)
118       .onProjectsDeleted(any());
119
120     underTestWithListeners.onProjectsDeleted(projects);
121
122     inOrder.verify(listener1).onProjectsDeleted(same(projects));
123     inOrder.verify(listener2).onProjectsDeleted(same(projects));
124     inOrder.verify(listener3).onProjectsDeleted(same(projects));
125     inOrder.verifyNoMoreInteractions();
126   }
127
128   @Test
129   public void onProjectBranchesDeleted_throws_NPE_if_set_is_null() {
130     assertThatThrownBy(() -> underTestWithListeners.onProjectBranchesDeleted(null))
131       .isInstanceOf(NullPointerException.class)
132       .hasMessage("projects can't be null");
133   }
134
135   @Test
136   public void onProjectBranchesDeleted_throws_NPE_if_set_is_null_even_if_no_listeners() {
137     assertThatThrownBy(() -> underTestNoListeners.onProjectBranchesDeleted(null))
138       .isInstanceOf(NullPointerException.class)
139       .hasMessage("projects can't be null");
140   }
141
142   @Test
143   public void onProjectBranchesDeleted_has_no_effect_if_set_is_empty() {
144     underTestNoListeners.onProjectBranchesDeleted(Collections.emptySet());
145
146     underTestWithListeners.onProjectBranchesDeleted(Collections.emptySet());
147     verifyNoInteractions(listener1, listener2, listener3);
148   }
149
150   @Test
151   @UseDataProvider("oneOrManyProjects")
152   public void onProjectBranchesDeleted_does_not_fail_if_there_is_no_listener(Set<Project> projects) {
153     underTestNoListeners.onProjectBranchesDeleted(projects);
154   }
155
156   @Test
157   @UseDataProvider("oneOrManyProjects")
158   public void onProjectBranchesDeleted_calls_all_listeners_in_order_of_addition_to_constructor(Set<Project> projects) {
159     InOrder inOrder = Mockito.inOrder(listener1, listener2, listener3);
160
161     underTestWithListeners.onProjectBranchesDeleted(projects);
162
163     inOrder.verify(listener1).onProjectBranchesDeleted(same(projects));
164     inOrder.verify(listener2).onProjectBranchesDeleted(same(projects));
165     inOrder.verify(listener3).onProjectBranchesDeleted(same(projects));
166     inOrder.verifyNoMoreInteractions();
167   }
168
169   @Test
170   @UseDataProvider("oneOrManyProjects")
171   public void onProjectBranchesDeleted_calls_all_listeners_even_if_one_throws_an_Exception(Set<Project> projects) {
172     InOrder inOrder = Mockito.inOrder(listener1, listener2, listener3);
173     doThrow(new RuntimeException("Faking listener2 throwing an exception"))
174       .when(listener2)
175       .onProjectBranchesDeleted(any());
176
177     underTestWithListeners.onProjectBranchesDeleted(projects);
178
179     inOrder.verify(listener1).onProjectBranchesDeleted(same(projects));
180     inOrder.verify(listener2).onProjectBranchesDeleted(same(projects));
181     inOrder.verify(listener3).onProjectBranchesDeleted(same(projects));
182     inOrder.verifyNoMoreInteractions();
183   }
184
185   @Test
186   @UseDataProvider("oneOrManyProjects")
187   public void onProjectBranchesDeleted_calls_all_listeners_even_if_one_throws_an_Error(Set<Project> projects) {
188     InOrder inOrder = Mockito.inOrder(listener1, listener2, listener3);
189     doThrow(new Error("Faking listener2 throwing an Error"))
190       .when(listener2)
191       .onProjectBranchesDeleted(any());
192
193     underTestWithListeners.onProjectBranchesDeleted(projects);
194
195     inOrder.verify(listener1).onProjectBranchesDeleted(same(projects));
196     inOrder.verify(listener2).onProjectBranchesDeleted(same(projects));
197     inOrder.verify(listener3).onProjectBranchesDeleted(same(projects));
198     inOrder.verifyNoMoreInteractions();
199   }
200
201   @DataProvider
202   public static Object[][] oneOrManyProjects() {
203     return new Object[][] {
204       {singleton(newUniqueProject())},
205       {IntStream.range(0, 1 + new Random().nextInt(10)).mapToObj(i -> newUniqueProject()).collect(Collectors.toSet())}
206     };
207   }
208
209   @DataProvider
210   public static Object[][] oneOrManyDeletedProjects() {
211     return new Object[][] {
212       {singleton(newUniqueProject())},
213       {IntStream.range(0, 1 + new Random().nextInt(10)).mapToObj(i -> new DeletedProject(newUniqueProject(), "branch_" + i))
214         .collect(Collectors.toSet())}
215     };
216   }
217
218
219   @Test
220   public void onProjectsRekeyed_throws_NPE_if_set_is_null() {
221     assertThatThrownBy(() -> underTestWithListeners.onProjectsRekeyed(null))
222       .isInstanceOf(NullPointerException.class)
223       .hasMessage("rekeyedProjects can't be null");
224   }
225
226   @Test
227   public void onProjectsRekeyed_throws_NPE_if_set_is_null_even_if_no_listeners() {
228     assertThatThrownBy(() -> underTestNoListeners.onProjectsRekeyed(null))
229       .isInstanceOf(NullPointerException.class)
230       .hasMessage("rekeyedProjects can't be null");
231   }
232
233   @Test
234   public void onProjectsRekeyed_has_no_effect_if_set_is_empty() {
235     underTestNoListeners.onProjectsRekeyed(Collections.emptySet());
236
237     underTestWithListeners.onProjectsRekeyed(Collections.emptySet());
238     verifyNoInteractions(listener1, listener2, listener3);
239   }
240
241   @Test
242   @UseDataProvider("oneOrManyRekeyedProjects")
243   public void onProjectsRekeyed_does_not_fail_if_there_is_no_listener(Set<RekeyedProject> projects) {
244     underTestNoListeners.onProjectsRekeyed(projects);
245   }
246
247   @Test
248   @UseDataProvider("oneOrManyRekeyedProjects")
249   public void onProjectsRekeyed_calls_all_listeners_in_order_of_addition_to_constructor(Set<RekeyedProject> projects) {
250     InOrder inOrder = Mockito.inOrder(listener1, listener2, listener3);
251
252     underTestWithListeners.onProjectsRekeyed(projects);
253
254     inOrder.verify(listener1).onProjectsRekeyed(same(projects));
255     inOrder.verify(listener2).onProjectsRekeyed(same(projects));
256     inOrder.verify(listener3).onProjectsRekeyed(same(projects));
257     inOrder.verifyNoMoreInteractions();
258   }
259
260   @Test
261   @UseDataProvider("oneOrManyRekeyedProjects")
262   public void onProjectsRekeyed_calls_all_listeners_even_if_one_throws_an_Exception(Set<RekeyedProject> projects) {
263     InOrder inOrder = Mockito.inOrder(listener1, listener2, listener3);
264     doThrow(new RuntimeException("Faking listener2 throwing an exception"))
265       .when(listener2)
266       .onProjectsRekeyed(any());
267
268     underTestWithListeners.onProjectsRekeyed(projects);
269
270     inOrder.verify(listener1).onProjectsRekeyed(same(projects));
271     inOrder.verify(listener2).onProjectsRekeyed(same(projects));
272     inOrder.verify(listener3).onProjectsRekeyed(same(projects));
273     inOrder.verifyNoMoreInteractions();
274   }
275
276   @Test
277   @UseDataProvider("oneOrManyRekeyedProjects")
278   public void onProjectsRekeyed_calls_all_listeners_even_if_one_throws_an_Error(Set<RekeyedProject> projects) {
279     InOrder inOrder = Mockito.inOrder(listener1, listener2, listener3);
280     doThrow(new Error("Faking listener2 throwing an Error"))
281       .when(listener2)
282       .onProjectsRekeyed(any());
283
284     underTestWithListeners.onProjectsRekeyed(projects);
285
286     inOrder.verify(listener1).onProjectsRekeyed(same(projects));
287     inOrder.verify(listener2).onProjectsRekeyed(same(projects));
288     inOrder.verify(listener3).onProjectsRekeyed(same(projects));
289     inOrder.verifyNoMoreInteractions();
290   }
291
292   @DataProvider
293   public static Object[][] oneOrManyRekeyedProjects() {
294     return new Object[][] {
295       {singleton(newUniqueRekeyedProject())},
296       {IntStream.range(0, 1 + new Random().nextInt(10)).mapToObj(i -> newUniqueRekeyedProject()).collect(Collectors.toSet())}
297     };
298   }
299
300   private static Project newUniqueProject() {
301     return Project.from(newPrivateProjectDto());
302   }
303
304   private static int counter = 3_989;
305
306   private static RekeyedProject newUniqueRekeyedProject() {
307     int base = counter++;
308     Project project = Project.from(newPrivateProjectDto());
309     return new RekeyedProject(project, base + "_old_key");
310   }
311 }