View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one
3    * or more contributor license agreements.  See the NOTICE file
4    * distributed with this work for additional information
5    * regarding copyright ownership.  The ASF licenses this file
6    * to you under the Apache License, Version 2.0 (the
7    * "License"); you may not use this file except in compliance
8    * with the License.  You may obtain a copy of the License at
9    *
10   *   http://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing,
13   * software distributed under the License is distributed on an
14   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   * KIND, either express or implied.  See the License for the
16   * specific language governing permissions and limitations
17   * under the License.
18   */
19  package org.apache.maven.surefire.api.testset;
20  
21  import java.util.ArrayList;
22  import java.util.Collection;
23  import java.util.Collections;
24  import java.util.HashSet;
25  import java.util.Iterator;
26  import java.util.LinkedHashSet;
27  import java.util.Set;
28  
29  import junit.framework.TestCase;
30  
31  import static java.util.Arrays.asList;
32  import static java.util.Collections.addAll;
33  import static java.util.Collections.emptySet;
34  import static java.util.Collections.singleton;
35  import static org.apache.maven.surefire.api.testset.ResolvedTest.Type.CLASS;
36  import static org.apache.maven.surefire.api.testset.TestListResolver.newTestListResolver;
37  import static org.hamcrest.MatcherAssert.assertThat;
38  import static org.hamcrest.Matchers.is;
39  
40  /**
41   *
42   */
43  public class TestListResolverTest extends TestCase {
44      private static final String DEFAULT_SUREFIRE_INCLUDED_TEST_PATTERNS =
45              "**/Test*.java, **/*Test.java, **/*TestCase.java";
46  
47      private static final String DEFAULT_SUREFIRE_EXCLUDED_TEST_PATTERNS = "**/*$*";
48  
49      public void testRegexSanity1() {
50          try {
51              TestListResolver.isRegexPrefixedPattern("#%regex[]");
52              fail("#%regex[]");
53          } catch (IllegalArgumentException e) {
54              // expected in junit 3.x
55          }
56      }
57  
58      public void testRegexSanity2() {
59          try {
60              TestListResolver.isRegexPrefixedPattern("%regex[]#");
61              fail("%regex[]#");
62          } catch (IllegalArgumentException e) {
63              // expected in junit 3.x
64          }
65      }
66  
67      public void testRegexSanity3() {
68          try {
69              TestListResolver.isRegexPrefixedPattern("%regex[]%regex[]");
70              fail("%regex[]%regex[]");
71          } catch (IllegalArgumentException e) {
72              // expected in junit 3.x
73          }
74      }
75  
76      public void testMinRegexLength() {
77          assertFalse(TestListResolver.isRegexMinLength("%regex[]"));
78          assertFalse(TestListResolver.isRegexMinLength("%regex[ ]"));
79          assertTrue(TestListResolver.isRegexMinLength("%regex[*Test]"));
80      }
81  
82      public void testRemoveExclamationMark() {
83          String pattern = TestListResolver.removeExclamationMark("!%regex[]");
84          assertEquals("%regex[]", pattern);
85          pattern = TestListResolver.removeExclamationMark("%regex[]");
86          assertEquals("%regex[]", pattern);
87      }
88  
89      public void testUnwrapped() {
90          String[] classAndMethod = TestListResolver.unwrap(" MyTest ");
91          assertEquals("MyTest", classAndMethod[0]);
92          assertEquals("", classAndMethod[1]);
93          classAndMethod = TestListResolver.unwrap(" # test ");
94          assertEquals("", classAndMethod[0]);
95          assertEquals("test", classAndMethod[1]);
96          classAndMethod = TestListResolver.unwrap(" MyTest # test ");
97          assertEquals("MyTest", classAndMethod[0]);
98          assertEquals("test", classAndMethod[1]);
99      }
100 
101     public void testUnwrappedRegex() {
102         String[] classAndMethod = TestListResolver.unwrapRegex("%regex[ .*.MyTest.class ]");
103         assertEquals(".*.MyTest.class", classAndMethod[0]);
104         assertEquals("", classAndMethod[1]);
105         classAndMethod = TestListResolver.unwrapRegex("%regex[ # myMethod|secondTest ]");
106         assertEquals("", classAndMethod[0]);
107         assertEquals("myMethod|secondTest", classAndMethod[1]);
108         classAndMethod = TestListResolver.unwrapRegex("%regex[ .*.MyTest.class # myMethod|secondTest ]");
109         assertEquals(".*.MyTest.class", classAndMethod[0]);
110         assertEquals("myMethod|secondTest", classAndMethod[1]);
111     }
112 
113     public void testMakeRegex() {
114         String regex = ResolvedTest.wrapRegex(".*.MyTest.class");
115         assertEquals("%regex[.*.MyTest.class]", regex);
116     }
117 
118     public void testNonRegexClassAndMethod() {
119         Collection<ResolvedTest> includedFilters = new ArrayList<>();
120         Collection<ResolvedTest> excludedFilters = new ArrayList<>();
121         IncludedExcludedPatterns includedExcludedPatterns = new IncludedExcludedPatterns();
122         TestListResolver.nonRegexClassAndMethods(
123                 "MyTest", "myTest", false, includedExcludedPatterns, includedFilters, excludedFilters);
124         assertTrue(includedExcludedPatterns.hasIncludedMethodPatterns);
125         assertFalse(includedExcludedPatterns.hasExcludedMethodPatterns);
126         assertFalse(includedFilters.isEmpty());
127         assertTrue(excludedFilters.isEmpty());
128         assertEquals(1, includedFilters.size());
129         ResolvedTest test = includedFilters.iterator().next();
130         assertFalse(test.isEmpty());
131         assertFalse(test.isRegexTestClassPattern());
132         assertFalse(test.isRegexTestMethodPattern());
133         assertTrue(test.hasTestClassPattern());
134         assertTrue(test.hasTestMethodPattern());
135         assertEquals("**/MyTest", test.getTestClassPattern());
136         assertEquals("myTest", test.getTestMethodPattern());
137         assertTrue(test.matchAsInclusive("MyTest", "myTest"));
138         assertFalse(test.matchAsInclusive("MyTest", "otherTest"));
139     }
140 
141     public void testNonRegexClassAndMethods() {
142         Collection<ResolvedTest> includedFilters = new ArrayList<>();
143         Collection<ResolvedTest> excludedFilters = new ArrayList<>();
144         IncludedExcludedPatterns includedExcludedPatterns = new IncludedExcludedPatterns();
145         TestListResolver.nonRegexClassAndMethods(
146                 "MyTest.class", "first*+second*", false, includedExcludedPatterns, includedFilters, excludedFilters);
147         assertTrue(includedExcludedPatterns.hasIncludedMethodPatterns);
148         assertFalse(includedExcludedPatterns.hasExcludedMethodPatterns);
149         assertFalse(includedFilters.isEmpty());
150         assertTrue(excludedFilters.isEmpty());
151         assertEquals(2, includedFilters.size());
152         Iterator<ResolvedTest> tests = includedFilters.iterator();
153         ResolvedTest first = tests.next();
154         assertFalse(first.isEmpty());
155         assertFalse(first.isRegexTestClassPattern());
156         assertFalse(first.isRegexTestMethodPattern());
157         assertTrue(first.hasTestClassPattern());
158         assertTrue(first.hasTestMethodPattern());
159         assertEquals("**/MyTest.class", first.getTestClassPattern());
160         assertEquals("first*", first.getTestMethodPattern());
161         assertTrue(first.matchAsInclusive("your/pkg/MyTest.class", "firstTest"));
162         ResolvedTest second = tests.next();
163         assertFalse(second.isEmpty());
164         assertFalse(second.isRegexTestClassPattern());
165         assertFalse(second.isRegexTestMethodPattern());
166         assertTrue(second.hasTestClassPattern());
167         assertTrue(second.hasTestMethodPattern());
168         assertEquals("**/MyTest.class", second.getTestClassPattern());
169         assertEquals("second*", second.getTestMethodPattern());
170         assertTrue(second.matchAsInclusive("your/pkg/MyTest.class", "secondTest"));
171         assertFalse(second.matchAsInclusive("your/pkg/MyTest.class", "thirdTest"));
172     }
173 
174     public void testNegativeNonRegexClassAndMethod() {
175         Collection<ResolvedTest> includedFilters = new ArrayList<>();
176         Collection<ResolvedTest> excludedFilters = new ArrayList<>();
177         IncludedExcludedPatterns includedExcludedPatterns = new IncludedExcludedPatterns();
178         TestListResolver.nonRegexClassAndMethods(
179                 "MyTest", "myTest", true, includedExcludedPatterns, includedFilters, excludedFilters);
180         assertFalse(includedExcludedPatterns.hasIncludedMethodPatterns);
181         assertTrue(includedExcludedPatterns.hasExcludedMethodPatterns);
182         assertTrue(includedFilters.isEmpty());
183         assertEquals(1, excludedFilters.size());
184         ResolvedTest test = excludedFilters.iterator().next();
185         assertFalse(test.isEmpty());
186         assertFalse(test.isRegexTestClassPattern());
187         assertFalse(test.isRegexTestMethodPattern());
188         assertTrue(test.hasTestClassPattern());
189         assertTrue(test.hasTestMethodPattern());
190         assertEquals("**/MyTest", test.getTestClassPattern());
191         assertEquals("myTest", test.getTestMethodPattern());
192         // ResolvedTest should not care about isExcluded. This attribute is handled by TestListResolver.
193         assertTrue(test.matchAsInclusive("MyTest", "myTest"));
194         assertFalse(test.matchAsInclusive("MyTest", "otherTest"));
195         assertFalse(test.matchAsInclusive("pkg/OtherTest.class", "myTest"));
196     }
197 
198     public void testResolveTestRequest() {
199         Collection<ResolvedTest> includedFilters = new ArrayList<>();
200         Collection<ResolvedTest> excludedFilters = new ArrayList<>();
201         IncludedExcludedPatterns includedExcludedPatterns = new IncludedExcludedPatterns();
202         TestListResolver.resolveTestRequest(
203                 "!%regex[.*.MyTest.class#myTest]", includedExcludedPatterns, includedFilters, excludedFilters);
204         assertFalse(includedExcludedPatterns.hasIncludedMethodPatterns);
205         assertTrue(includedExcludedPatterns.hasExcludedMethodPatterns);
206         assertTrue(includedFilters.isEmpty());
207         assertFalse(excludedFilters.isEmpty());
208         assertEquals(1, excludedFilters.size());
209         ResolvedTest test = excludedFilters.iterator().next();
210         // ResolvedTest should not care about isExcluded. This attribute is handled by TestListResolver.
211         assertTrue(test.matchAsInclusive("pkg/MyTest.class", "myTest"));
212         assertFalse(test.matchAsInclusive("pkg/MyTest.class", "otherTest"));
213         assertFalse(test.matchAsInclusive("pkg/OtherTest.class", "myTest"));
214     }
215 
216     public void testShouldRunTestWithoutMethod() {
217         new TestListResolver("**/*Test.class, !%regex[.*.MyTest.class#myTest]").shouldRun("pkg/MyTest.class", null);
218     }
219 
220     public void testShouldNotRunExcludedMethods() {
221         TestListResolver resolver = new TestListResolver("!#*Fail*, !%regex[#.*One], !#testSuccessThree");
222         assertTrue(resolver.shouldRun("pkg/MyTest.class", null));
223     }
224 
225     public void testShouldRunSuiteWithIncludedMethods() {
226         TestListResolver resolver = new TestListResolver("#*Fail*, %regex[#.*One], #testSuccessThree");
227         assertTrue(resolver.shouldRun("pkg/MyTest.class", null));
228     }
229 
230     public void testShouldRunAny() {
231         TestListResolver resolver = TestListResolver.getEmptyTestListResolver();
232         assertTrue(resolver.shouldRun("pkg/MyTest.class", null));
233 
234         resolver = new TestListResolver(Collections.<String>emptySet());
235         assertTrue(resolver.shouldRun("pkg/MyTest.class", null));
236     }
237 
238     public void testClassFilter() {
239         TestListResolver resolver = new TestListResolver("#test");
240         assertTrue(resolver.shouldRun("pkg/MyTest.class", null));
241 
242         resolver = new TestListResolver("!#test");
243         assertTrue(resolver.shouldRun("pkg/MyTest.class", null));
244 
245         resolver = new TestListResolver("SomeOtherClass");
246         assertFalse(resolver.shouldRun("pkg/MyTest.class", null));
247     }
248 
249     public void testBrokenPatternThrowsException() {
250         Collection<String> included = emptySet();
251         Collection<String> excluded = asList("BasicTest, !**/TestTwo, **/TestThree.java");
252         try {
253             new TestListResolver(included, excluded);
254             fail("Expected: IllegalArgumentException");
255         } catch (IllegalArgumentException e) {
256             // JUnit 3.x style
257             assertEquals(
258                     "Exclamation mark not expected in 'exclusion': BasicTest, !**/TestTwo, **/TestThree.java",
259                     e.getLocalizedMessage());
260         }
261     }
262 
263     public void testMultipleExcludedClassesOnly() {
264         Collection<String> included = emptySet();
265         Collection<String> excluded = asList("BasicTest, **/TestTwo, **/TestThree.java");
266         TestListResolver resolver = new TestListResolver(included, excluded);
267         assertFalse(resolver.shouldRun("jiras/surefire745/BasicTest.class", null));
268         assertFalse(resolver.shouldRun("jiras/surefire745/TestTwo.class", null));
269         assertFalse(resolver.shouldRun("jiras/surefire745/TestThree.class", null));
270         assertTrue(resolver.shouldRun("jiras/surefire745/TestFour.class", null));
271     }
272 
273     public void testMultipleExcludedClasses() {
274         Collection<String> included = singleton(DEFAULT_SUREFIRE_INCLUDED_TEST_PATTERNS);
275         Collection<String> excluded = asList("BasicTest, **/TestTwo, **/TestThree.java");
276         TestListResolver resolver = new TestListResolver(included, excluded);
277         assertFalse(resolver.shouldRun("jiras/surefire745/BasicTest.class", null));
278         assertFalse(resolver.shouldRun("jiras/surefire745/TestTwo.class", null));
279         assertFalse(resolver.shouldRun("jiras/surefire745/TestThree.class", null));
280         assertTrue(resolver.shouldRun("jiras/surefire745/TestFour.class", null));
281     }
282 
283     public void testAndFilters() {
284         TestListResolver firstFilter = new TestListResolver("BasicTest, **/TestTwo, **/TestThree.java");
285         TestListResolver secondFilter = new TestListResolver("*icTest, Test???*");
286         TestFilter<String, String> filter = firstFilter.and(secondFilter);
287 
288         assertTrue(filter.shouldRun("jiras/surefire745/BasicTest.class", null));
289         assertTrue(filter.shouldRun("jiras/surefire745/TestTwo.class", null));
290         assertTrue(filter.shouldRun("jiras/surefire745/TestThree.class", null));
291         assertFalse(filter.shouldRun("jiras/surefire745/TestFour.class", null));
292     }
293 
294     public void testTestListResolverWithoutMethods() {
295         ResolvedTest inc1 = new ResolvedTest("A?Test.java", null, false);
296         ResolvedTest inc2 = new ResolvedTest("**/?Test", null, false);
297         ResolvedTest exc1 = new ResolvedTest("AATest", null, false);
298         ResolvedTest exc2 = new ResolvedTest("**/BTest.java", null, false);
299         TestListResolver resolver = newTestListResolver(toSet(inc1, inc2), toSet(exc1, exc2));
300         assertThat(resolver.getPluginParameterTest(), is("A?Test.java, **/?Test, !AATest, !**/BTest.java"));
301         assertFalse(resolver.isEmpty());
302         assertFalse(resolver.hasIncludedMethodPatterns());
303         assertFalse(resolver.hasExcludedMethodPatterns());
304         assertFalse(resolver.hasMethodPatterns());
305         assertTrue(resolver.shouldRun("ATest.class", null));
306         assertFalse(resolver.shouldRun("AATest.class", null));
307         assertTrue(resolver.shouldRun("ABTest.class", null));
308         assertFalse(resolver.shouldRun("BTest.class", null));
309         assertTrue(resolver.shouldRun("CTest.class", null));
310         assertFalse(resolver.hasMethodPatterns());
311     }
312 
313     public void testTestListResolverWithMethods() {
314         ResolvedTest inc1 = new ResolvedTest("A?Test.java", null, false);
315         ResolvedTest inc2 = new ResolvedTest("*?Test", null, false);
316         ResolvedTest exc1 = new ResolvedTest("AATest", null, false);
317         ResolvedTest exc2 = new ResolvedTest("*BTest.java", "failedTest", false);
318         TestListResolver resolver = newTestListResolver(toSet(inc1, inc2), toSet(exc1, exc2));
319         assertThat(resolver.getPluginParameterTest(), is("A?Test.java, *?Test, !AATest, !*BTest.java#failedTest"));
320         assertFalse(resolver.isEmpty());
321         assertFalse(resolver.hasIncludedMethodPatterns());
322         assertTrue(resolver.hasExcludedMethodPatterns());
323         assertTrue(resolver.hasMethodPatterns());
324         assertTrue(resolver.shouldRun("ATest.class", null));
325         assertFalse(resolver.shouldRun("AATest.class", null));
326         assertTrue(resolver.shouldRun("ABTest.class", null));
327         assertTrue(resolver.shouldRun("BTest.class", null));
328         assertFalse(resolver.shouldRun("BTest.class", "failedTest"));
329         assertTrue(resolver.shouldRun("CTest.class", null));
330         assertFalse(TestListResolver.optionallyWildcardFilter(resolver).isEmpty());
331     }
332 
333     private static Set<ResolvedTest> toSet(ResolvedTest... patterns) {
334         Set<ResolvedTest> set = new LinkedHashSet<>();
335         addAll(set, patterns);
336         return set;
337     }
338 
339     public void testDefaultPatternsMatching() {
340         Set<ResolvedTest> inclusions = resolveClass(DEFAULT_SUREFIRE_INCLUDED_TEST_PATTERNS);
341         Set<ResolvedTest> exclusions = resolveClass(DEFAULT_SUREFIRE_EXCLUDED_TEST_PATTERNS);
342         TestListResolver tlr = newTestListResolver(inclusions, exclusions);
343         boolean shouldRun = tlr.shouldRun("org/apache/maven/surefire/SomeTest.class", null);
344         assertTrue(shouldRun);
345     }
346 
347     public void testDefaultPatternsNotMatching() {
348         Set<ResolvedTest> inclusions = resolveClass(DEFAULT_SUREFIRE_INCLUDED_TEST_PATTERNS);
349         Set<ResolvedTest> exclusions = resolveClass(DEFAULT_SUREFIRE_EXCLUDED_TEST_PATTERNS);
350         TestListResolver tlr = newTestListResolver(inclusions, exclusions);
351         boolean shouldRun = tlr.shouldRun("org/apache/maven/surefire/SomeTestNotRunning.class", null);
352         assertFalse(shouldRun);
353     }
354 
355     public void testInclusiveWithDefaultExclusivePattern() {
356         Set<ResolvedTest> defaultExclusions = resolveClass(DEFAULT_SUREFIRE_EXCLUDED_TEST_PATTERNS);
357         boolean runnable = newTestListResolver(resolveClass("A*Test"), defaultExclusions)
358                 .shouldRun("org/apache/maven/surefire/ARunnableTest.class", null);
359         assertTrue(runnable);
360     }
361 
362     public void testWildcard() {
363         TestListResolver tlr = TestListResolver.optionallyWildcardFilter(new TestListResolver((String) null));
364         assertThat(tlr, is(new TestListResolver("**/*.class")));
365         assertThat(tlr.isWildcard(), is(true));
366         assertThat(tlr.isEmpty(), is(false));
367 
368         tlr = TestListResolver.optionallyWildcardFilter(new TestListResolver("**/**/MethodLessPattern.class"));
369         assertThat(tlr, is(new TestListResolver("**/*.class")));
370         assertThat(tlr.isWildcard(), is(true));
371         assertThat(tlr.isEmpty(), is(false));
372     }
373 
374     public void testRegexRuleViolationQuotedHashMark() {
375         try {
376             new TestListResolver("%regex[.\\Q#\\E.]");
377             fail("IllegalArgumentException is expected");
378         } catch (IllegalArgumentException iea) {
379             // expected
380         }
381     }
382 
383     public void testRegexRuleViolationEnclosedMethodSeparator() {
384         try {
385             new TestListResolver("%regex[(.|.#.)]");
386             fail("IllegalArgumentException is expected");
387         } catch (IllegalArgumentException iea) {
388             // expected
389         }
390     }
391 
392     public void testRegexRuleViolationMultipleHashmarkWithClassConstraint() {
393         try {
394             new TestListResolver("%regex[.*#.|#.]");
395             fail("IllegalArgumentException is expected");
396         } catch (IllegalArgumentException iea) {
397             // expected
398         }
399     }
400 
401     public void testRegexRuleViolationMultipleHashmarkForMethods() {
402         try {
403             new TestListResolver("%regex[#.|#.]");
404             fail("IllegalArgumentException is expected");
405         } catch (IllegalArgumentException iea) {
406             // expected
407         }
408     }
409 
410     public void testRegexRuleViolationInvalidClassPattern() {
411         try {
412             new TestListResolver("%regex[.(.]").shouldRun("x", "x");
413             fail("IllegalArgumentException is expected");
414         } catch (IllegalArgumentException iea) {
415             // expected
416         }
417     }
418 
419     public void testRegexRuleViolationInvalidMethodPattern() {
420         try {
421             new TestListResolver("%regex[#.(.]");
422             fail("IllegalArgumentException is expected");
423         } catch (IllegalArgumentException iea) {
424             // expected
425         }
426     }
427 
428     private static Set<ResolvedTest> resolveClass(String patterns) {
429         Set<ResolvedTest> resolved = new HashSet<>();
430         for (String pattern : patterns.split(",")) {
431             resolved.add(new ResolvedTest(CLASS, pattern, false));
432         }
433         return resolved;
434     }
435 }