View Javadoc

1   package org.apache.maven.plugin.surefire;
2   
3   /*
4    * Licensed to the Apache Software Foundation (ASF) under one
5    * or more contributor license agreements.  See the NOTICE file
6    * distributed with this work for additional information
7    * regarding copyright ownership.  The ASF licenses this file
8    * to you under the Apache License, Version 2.0 (the
9    * "License"); you may not use this file except in compliance
10   * with the License.  You may obtain a copy of the License at
11   *
12   *     http://www.apache.org/licenses/LICENSE-2.0
13   *
14   * Unless required by applicable law or agreed to in writing,
15   * software distributed under the License is distributed on an
16   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
17   * KIND, either express or implied.  See the License for the
18   * specific language governing permissions and limitations
19   * under the License.
20   */
21  
22  import java.io.File;
23  import java.util.List;
24  import org.apache.maven.plugin.MojoExecutionException;
25  import org.apache.maven.plugin.MojoFailureException;
26  import org.apache.maven.plugins.annotations.LifecyclePhase;
27  import org.apache.maven.plugins.annotations.Mojo;
28  import org.apache.maven.plugins.annotations.Parameter;
29  import org.apache.maven.plugins.annotations.ResolutionScope;
30  import org.apache.maven.surefire.suite.RunResult;
31  import org.apache.maven.surefire.util.internal.StringUtils;
32  
33  /**
34   * Run tests using Surefire.
35   *
36   * @author Jason van Zyl
37   * @noinspection JavaDoc
38   */
39  @Mojo( name = "test", defaultPhase = LifecyclePhase.TEST, threadSafe = true,
40         requiresDependencyResolution = ResolutionScope.TEST )
41  public class SurefirePlugin
42      extends AbstractSurefireMojo
43      implements SurefireReportParameters
44  {
45  
46      /**
47       * Set this to "true" to ignore a failure during testing. Its use is NOT RECOMMENDED, but quite convenient on
48       * occasion.
49       */
50      @Parameter( property = "maven.test.failure.ignore", defaultValue = "false" )
51      private boolean testFailureIgnore;
52  
53      /**
54       * Base directory where all reports are written to.
55       */
56      @Parameter( defaultValue = "${project.build.directory}/surefire-reports" )
57      private File reportsDirectory;
58  
59      /**
60       * Specify this parameter to run individual tests by file name, overriding the <code>includes/excludes</code>
61       * parameters. Each pattern you specify here will be used to create an include pattern formatted like
62       * <code>**&#47;${test}.java</code>, so you can just type "-Dtest=MyTest" to run a single test called
63       * "foo/MyTest.java". The test patterns prefixed with a <code>!</code> will be excluded.<br/>
64       * This parameter overrides the <code>includes/excludes</code> parameters, and the TestNG <code>suiteXmlFiles</code>
65       * parameter.
66       * <p/>
67       * Since 2.7.3, you can execute a limited number of methods in the test by adding #myMethod or #my*ethod. For example,
68       * "-Dtest=MyTest#myMethod".  This is supported for junit 4.x and testNg.
69       */
70      @Parameter( property = "test" )
71      private String test;
72  
73      /**
74       * Option to print summary of test suites or just print the test cases that have errors.
75       */
76      @Parameter( property = "surefire.printSummary", defaultValue = "true" )
77      private boolean printSummary;
78  
79      /**
80       * Selects the formatting for the test report to be generated. Can be set as "brief" or "plain".
81       * Only applies to the output format of the output files  (target/surefire-reports/testName.txt)
82       */
83      @Parameter( property = "surefire.reportFormat", defaultValue = "brief" )
84      private String reportFormat;
85  
86      /**
87       * Option to generate a file test report or just output the test report to the console.
88       */
89      @Parameter( property = "surefire.useFile", defaultValue = "true" )
90      private boolean useFile;
91  
92  
93      /**
94       * Set this to "true" to cause a failure if the none of the tests specified in -Dtest=... are run. Defaults to
95       * "true".
96       *
97       * @since 2.12
98       */
99      @Parameter( property = "surefire.failIfNoSpecifiedTests" )
100     private Boolean failIfNoSpecifiedTests;
101 
102     /**
103      * Attach a debugger to the forked JVM. If set to "true", the process will suspend and wait for a debugger to attach
104      * on port 5005. If set to some other string, that string will be appended to the argLine, allowing you to configure
105      * arbitrary debuggability options (without overwriting the other options specified through the <code>argLine</code>
106      * parameter).
107      *
108      * @since 2.4
109      */
110     @Parameter( property = "maven.surefire.debug" )
111     private String debugForkedProcess;
112 
113     /**
114      * Kill the forked test process after a certain number of seconds. If set to 0, wait forever for the process, never
115      * timing out.
116      *
117      * @since 2.4
118      */
119     @Parameter( property = "surefire.timeout" )
120     private int forkedProcessTimeoutInSeconds;
121 
122     /**
123      * Stop executing queued parallel JUnit tests after a certain number of seconds.
124      * <br/>
125      * Example values: "3.5", "4"<br/>
126      * <br/>
127      * If set to 0, wait forever, never timing out.
128      * Makes sense with specified <code>parallel</code> different from "none".
129      *
130      * @since 2.16
131      */
132     @Parameter( property = "surefire.parallel.timeout" )
133     private double parallelTestsTimeoutInSeconds;
134 
135     /**
136      * Stop executing queued parallel JUnit tests
137      * and <em>interrupt</em> currently running tests after a certain number of seconds.
138      * <br/>
139      * Example values: "3.5", "4"<br/>
140      * <br/>
141      * If set to 0, wait forever, never timing out.
142      * Makes sense with specified <code>parallel</code> different from "none".
143      *
144      * @since 2.16
145      */
146     @Parameter( property = "surefire.parallel.forcedTimeout" )
147     private double parallelTestsTimeoutForcedInSeconds;
148     
149     /**
150      * A list of &lt;include> elements specifying the tests (by pattern) that should be included in testing. When not
151      * specified and when the <code>test</code> parameter is not specified, the default includes will be <code><br/>
152      * &lt;includes><br/>
153      * &nbsp;&lt;include>**&#47;Test*.java&lt;/include><br/>
154      * &nbsp;&lt;include>**&#47;*Test.java&lt;/include><br/>
155      * &nbsp;&lt;include>**&#47;*TestCase.java&lt;/include><br/>
156      * &lt;/includes><br/>
157      * </code>
158      * <p/>
159      * Each include item may also contain a comma-separated sublist of items, which will be treated as multiple
160      * &nbsp;&lt;include> entries.<br/>
161      * <p/>
162      * This parameter is ignored if the TestNG <code>suiteXmlFiles</code> parameter is specified.
163      */
164     @Parameter
165     private List<String> includes;
166 
167     /**
168      * Option to pass dependencies to the system's classloader instead of using an isolated class loader when forking.
169      * Prevents problems with JDKs which implement the service provider lookup mechanism by using the system's
170      * classloader.
171      *
172      * @since 2.3
173      */
174     @Parameter( property = "surefire.useSystemClassLoader", defaultValue = "true" )
175     private boolean useSystemClassLoader;
176 
177     /**
178      * By default, Surefire forks your tests using a manifest-only JAR; set this parameter to "false" to force it to
179      * launch your tests with a plain old Java classpath. (See
180      * http://maven.apache.org/plugins/maven-surefire-plugin/examples/class-loading.html for a more detailed explanation
181      * of manifest-only JARs and their benefits.)
182      * <p/>
183      * Beware, setting this to "false" may cause your tests to fail on Windows if your classpath is too long.
184      *
185      * @since 2.4.3
186      */
187     @Parameter( property = "surefire.useManifestOnlyJar", defaultValue = "true" )
188     private boolean useManifestOnlyJar;
189 
190     protected void handleSummary( RunResult summary, Exception firstForkException )
191         throws MojoExecutionException, MojoFailureException
192     {
193         assertNoException( firstForkException );
194 
195         SurefireHelper.reportExecution( this, summary, getLog() );
196     }
197 
198     private void assertNoException( Exception firstForkException )
199         throws MojoFailureException
200     {
201         if ( firstForkException != null )
202         {
203             throw new MojoFailureException( firstForkException.getMessage(), firstForkException );
204         }
205     }
206 
207     private void assertNoFailureOrTimeout( Exception summary )
208         throws MojoFailureException
209     {
210         if ( summary != null )
211         {
212             throw new MojoFailureException( "Failure or timeout" );
213         }
214     }
215 
216     protected boolean isSkipExecution()
217     {
218         return isSkip() || isSkipTests() || isSkipExec();
219     }
220 
221     protected String getPluginName()
222     {
223         return "surefire";
224     }
225 
226     protected String[] getDefaultIncludes()
227     {
228         return new String[]{ "**/Test*.java", "**/*Test.java", "**/*TestCase.java" };
229     }
230 
231     // now for the implementation of the field accessors
232 
233     public boolean isSkipTests()
234     {
235         return skipTests;
236     }
237 
238     public void setSkipTests( boolean skipTests )
239     {
240         this.skipTests = skipTests;
241     }
242 
243     /**
244      * @noinspection deprecation
245      */
246     public boolean isSkipExec()
247     {
248         return skipExec;
249     }
250 
251     /**
252      * @noinspection deprecation
253      */
254     public void setSkipExec( boolean skipExec )
255     {
256         this.skipExec = skipExec;
257     }
258 
259     public boolean isSkip()
260     {
261         return skip;
262     }
263 
264     public void setSkip( boolean skip )
265     {
266         this.skip = skip;
267     }
268 
269     public boolean isTestFailureIgnore()
270     {
271         return testFailureIgnore;
272     }
273 
274     public void setTestFailureIgnore( boolean testFailureIgnore )
275     {
276         this.testFailureIgnore = testFailureIgnore;
277     }
278 
279     public File getBasedir()
280     {
281         return basedir;
282     }
283 
284     public void setBasedir( File basedir )
285     {
286         this.basedir = basedir;
287     }
288 
289     public File getTestClassesDirectory()
290     {
291         return testClassesDirectory;
292     }
293 
294     public void setTestClassesDirectory( File testClassesDirectory )
295     {
296         this.testClassesDirectory = testClassesDirectory;
297     }
298 
299     public File getClassesDirectory()
300     {
301         return classesDirectory;
302     }
303 
304     public void setClassesDirectory( File classesDirectory )
305     {
306         this.classesDirectory = classesDirectory;
307     }
308 
309     public File getReportsDirectory()
310     {
311         return reportsDirectory;
312     }
313 
314     public void setReportsDirectory( File reportsDirectory )
315     {
316         this.reportsDirectory = reportsDirectory;
317     }
318 
319     public String getTest()
320     {
321         if ( StringUtils.isBlank( test ) )
322         {
323             return null;
324         }
325         String[] testArray = StringUtils.split( test, "," );
326         StringBuilder tests = new StringBuilder();
327         for ( String aTestArray : testArray )
328         {
329             String singleTest = aTestArray;
330             int index = singleTest.indexOf( '#' );
331             if ( index >= 0 )
332             {// the way version 2.7.3.  support single test method
333                 singleTest = singleTest.substring( 0, index );
334             }
335             tests.append( singleTest );
336             tests.append( "," );
337         }
338         return tests.toString();
339     }
340 
341     /**
342      * @since 2.7.3
343      */
344     public String getTestMethod()
345     {
346         if ( StringUtils.isBlank( test ) )
347         {
348             return null;
349         }
350         //modified by rainLee, see http://jira.codehaus.org/browse/SUREFIRE-745
351         int index = this.test.indexOf( '#' );
352         int index2 = this.test.indexOf( "," );
353         if ( index >= 0 )
354         {
355             if ( index2 < 0 )
356             {
357                 String testStrAfterFirstSharp = this.test.substring( index + 1, this.test.length() );
358                 if ( !testStrAfterFirstSharp.contains( "+" ) )
359                 {//the original way
360                     return testStrAfterFirstSharp;
361                 }
362                 else
363                 {
364                     return this.test;
365                 }
366             }
367             else
368             {
369                 return this.test;
370             }
371         }
372         return null;
373     }
374 
375     public boolean isUseSystemClassLoader()
376     {
377         return useSystemClassLoader;
378     }
379 
380     public void setUseSystemClassLoader( boolean useSystemClassLoader )
381     {
382         this.useSystemClassLoader = useSystemClassLoader;
383     }
384 
385     public boolean isUseManifestOnlyJar()
386     {
387         return useManifestOnlyJar;
388     }
389 
390     public void setUseManifestOnlyJar( boolean useManifestOnlyJar )
391     {
392         this.useManifestOnlyJar = useManifestOnlyJar;
393     }
394 
395     public Boolean getFailIfNoSpecifiedTests()
396     {
397         return failIfNoSpecifiedTests;
398     }
399 
400     public void setFailIfNoSpecifiedTests( Boolean failIfNoSpecifiedTests )
401     {
402         this.failIfNoSpecifiedTests = failIfNoSpecifiedTests;
403     }
404 
405     public boolean isPrintSummary()
406     {
407         return printSummary;
408     }
409 
410     public void setPrintSummary( boolean printSummary )
411     {
412         this.printSummary = printSummary;
413     }
414 
415     public String getReportFormat()
416     {
417         return reportFormat;
418     }
419 
420     public void setReportFormat( String reportFormat )
421     {
422         this.reportFormat = reportFormat;
423     }
424 
425     public boolean isUseFile()
426     {
427         return useFile;
428     }
429 
430     public void setUseFile( boolean useFile )
431     {
432         this.useFile = useFile;
433     }
434 
435     public String getDebugForkedProcess()
436     {
437         return debugForkedProcess;
438     }
439 
440     public void setDebugForkedProcess( String debugForkedProcess )
441     {
442         this.debugForkedProcess = debugForkedProcess;
443     }
444 
445     public int getForkedProcessTimeoutInSeconds()
446     {
447         return forkedProcessTimeoutInSeconds;
448     }
449 
450     public void setForkedProcessTimeoutInSeconds( int forkedProcessTimeoutInSeconds )
451     {
452         this.forkedProcessTimeoutInSeconds = forkedProcessTimeoutInSeconds;
453     }
454 
455     public double getParallelTestsTimeoutInSeconds() {
456         return parallelTestsTimeoutInSeconds;
457     }
458 
459     public void setParallelTestsTimeoutInSeconds( double parallelTestsTimeoutInSeconds ) {
460         this.parallelTestsTimeoutInSeconds = parallelTestsTimeoutInSeconds;
461     }
462 
463     public double getParallelTestsTimeoutForcedInSeconds() {
464         return parallelTestsTimeoutForcedInSeconds;
465     }
466 
467     public void setParallelTestsTimeoutForcedInSeconds( double parallelTestsTimeoutForcedInSeconds ) {
468         this.parallelTestsTimeoutForcedInSeconds = parallelTestsTimeoutForcedInSeconds;
469     }
470 
471     public void setTest( String test )
472     {
473         this.test = test;
474     }
475 
476     @Override
477     public List<String> getIncludes()
478     {
479         return includes;
480     }
481 
482     @Override
483     public void setIncludes( List<String> includes )
484     {
485         this.includes = includes;
486     }
487 }