Repository: maven-surefire Updated Branches: refs/heads/master e5a6b9c8d -> 201a31346 (forced update)
[SUREFIRE-1324] Surefire incorrectly suppresses exceptions when closing resources. Project: http://git-wip-us.apache.org/repos/asf/maven-surefire/repo Commit: http://git-wip-us.apache.org/repos/asf/maven-surefire/commit/201a3134 Tree: http://git-wip-us.apache.org/repos/asf/maven-surefire/tree/201a3134 Diff: http://git-wip-us.apache.org/repos/asf/maven-surefire/diff/201a3134 Branch: refs/heads/master Commit: 201a3134673f3794d71262bdf1cf057bbb3d1056 Parents: 66bc4c0 Author: Tibor17 <tibo...@lycos.com> Authored: Sat Jan 7 18:28:50 2017 +0100 Committer: Tibor17 <tibo...@lycos.com> Committed: Sat Jan 7 18:28:50 2017 +0100 ---------------------------------------------------------------------- .../plugin/surefire/SurefireProperties.java | 30 ++---- .../booterclient/ForkConfiguration.java | 7 +- .../output/LostCommandsDumpSingleton.java | 62 +++++++++++- .../output/ThreadedStreamConsumer.java | 35 ++++--- .../report/ConsoleOutputFileReporter.java | 8 +- .../plugin/surefire/report/FileReporter.java | 12 ++- .../surefire/runorder/StatisticsReporter.java | 3 +- .../maven/surefire/report/FileReporterTest.java | 6 +- .../surefire/report/SurefireReportMojoTest.java | 2 +- surefire-api/pom.xml | 4 + .../runorder/RunEntryStatisticsMap.java | 34 +++---- .../maven/surefire/booter/CommandReader.java | 21 ++--- .../surefire/booter/DumpErrorSingleton.java | 99 ++++++++++++++++++++ .../surefire/booter/ForkingRunListener.java | 21 ++++- .../surefire/booter/MasterProcessCommand.java | 26 +---- .../maven/surefire/booter/ForkedBooter.java | 25 +---- .../surefire/booter/SystemPropertyManager.java | 3 + .../maven/surefire/its/fixture/TestFile.java | 18 +++- .../src/test/java/it/BasicTest.java | 30 ++++-- .../src/test/java/runListener/FileHelper.java | 25 +++-- .../apache/maven/surefire/test/FailingTest.java | 15 +-- .../maven/surefire/test/SucceedingTest.java | 14 +-- .../plugins/surefire/dumppid/DumpPidMojo.java | 28 ++++-- .../src/test/java/listenReport/FileHelper.java | 28 ++++-- .../java/testng/objectfactory/FileHelper.java | 27 ++++-- .../testng/testrunnerfactory/FileHelper.java | 22 ++++- 26 files changed, 412 insertions(+), 193 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/SurefireProperties.java ---------------------------------------------------------------------- diff --git a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/SurefireProperties.java b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/SurefireProperties.java index 3663f39..53aa134 100644 --- a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/SurefireProperties.java +++ b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/SurefireProperties.java @@ -19,6 +19,10 @@ package org.apache.maven.plugin.surefire; * under the License. */ +import org.apache.maven.surefire.booter.Classpath; +import org.apache.maven.surefire.booter.KeyValueSource; +import org.apache.maven.surefire.util.internal.StringUtils; + import java.io.File; import java.io.FileInputStream; import java.io.IOException; @@ -33,11 +37,8 @@ import java.util.Map; import java.util.Properties; import java.util.Set; -import org.apache.maven.surefire.booter.Classpath; -import org.apache.maven.surefire.booter.KeyValueSource; -import org.apache.maven.surefire.util.internal.StringUtils; - import static java.util.Arrays.asList; +import static org.apache.maven.shared.utils.io.IOUtil.close; /** * A properties implementation that preserves insertion order. @@ -46,6 +47,7 @@ public class SurefireProperties extends Properties implements KeyValueSource { + private static final Collection<String> KEYS_THAT_CANNOT_BE_USED_AS_SYSTEM_PROPERTIES = asList( "java.library.path", "file.encoding", "jdk.map.althashing.threshold", "line.separator" ); @@ -153,7 +155,6 @@ public class SurefireProperties // user specified properties for SUREFIRE-121, causing SUREFIRE-491. // Not gonna do THAT any more... instead, we only propagate those system properties // that have been explicitly specified by the user via -Dkey=value on the CLI - result.copyPropertiesFrom( userProperties ); return result; } @@ -224,18 +225,18 @@ public class SurefireProperties } } - private static SurefireProperties loadProperties( InputStream inStream ) + private static SurefireProperties loadProperties( final InputStream inStream ) throws IOException { try { - Properties p = new Properties(); + final Properties p = new Properties(); p.load( inStream ); return new SurefireProperties( p ); } finally { - close( inStream ); + close( inStream ); // @todo use try-with-resources JDK7, search in all code } } @@ -245,18 +246,6 @@ public class SurefireProperties return file == null ? new SurefireProperties() : loadProperties( new FileInputStream( file ) ); } - private static void close( InputStream inputStream ) - { - try - { - inputStream.close(); - } - catch ( IOException ex ) - { - // ignore - } - } - public void setNullableProperty( String key, String value ) { if ( value != null ) @@ -264,4 +253,5 @@ public class SurefireProperties super.setProperty( key, value ); } } + } http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/ForkConfiguration.java ---------------------------------------------------------------------- diff --git a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/ForkConfiguration.java b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/ForkConfiguration.java index 988af8f..6cb0fab 100644 --- a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/ForkConfiguration.java +++ b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/ForkConfiguration.java @@ -23,6 +23,7 @@ import org.apache.maven.plugin.surefire.AbstractSurefireMojo; import org.apache.maven.plugin.surefire.booterclient.lazytestprovider.OutputStreamFlushableCommandline; import org.apache.maven.plugin.surefire.util.Relocator; import org.apache.maven.shared.utils.StringUtils; +import org.apache.maven.shared.utils.io.IOUtil; import org.apache.maven.surefire.booter.Classpath; import org.apache.maven.surefire.booter.ForkedBooter; import org.apache.maven.surefire.booter.StartupConfiguration; @@ -270,10 +271,10 @@ public class ForkConfiguration { file.deleteOnExit(); } - FileOutputStream fos = new FileOutputStream( file ); - JarOutputStream jos = new JarOutputStream( fos ); + JarOutputStream jos = null; try { + jos = new JarOutputStream( new FileOutputStream( file ) ); jos.setLevel( JarOutputStream.STORED ); JarEntry je = new JarEntry( "META-INF/MANIFEST.MF" ); jos.putNextEntry( je ); @@ -300,7 +301,7 @@ public class ForkConfiguration } finally { - jos.close(); + IOUtil.close( jos ); } return file; http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/output/LostCommandsDumpSingleton.java ---------------------------------------------------------------------- diff --git a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/output/LostCommandsDumpSingleton.java b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/output/LostCommandsDumpSingleton.java index 364d8c3..fa38c05 100644 --- a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/output/LostCommandsDumpSingleton.java +++ b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/output/LostCommandsDumpSingleton.java @@ -1 +1,61 @@ -package org.apache.maven.plugin.surefire.booterclient.output; /* * Licensed to the Apache Software Foundation (ASF) under one * or more contributor license agreements. See the NOTICE file * distributed with this work for additional information * regarding copyright ownership. The ASF licenses this file * to you under the Apache License, Version 2.0 (the * "License"); you may not use this file except in compliance * with the License. You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, * software distributed under the License is distributed on an * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY * KIND, either express or implied. See the License for the * specific language governing permissions and limitations * under the License. */ import org.apache.maven.plugin.surefire.report.DefaultReporterFactory; import org.apache.maven.surefire.util.internal.DumpF ileUtils; import java.io.File; /** * Dumps lost commands and caused exceptions in {@link ForkClient}. * * @author <a href="mailto:tibordig...@apache.org">Tibor Digana (tibor17)</a> * @since 2.19.2 */ final class LostCommandsDumpSingleton { private static final LostCommandsDumpSingleton SINGLETON = new LostCommandsDumpSingleton(); private final String creationDate = DumpFileUtils.newFormattedDateFileName(); private LostCommandsDumpSingleton() { } static LostCommandsDumpSingleton getSingleton() { return SINGLETON; } synchronized void dumpException( Throwable t, String msg, DefaultReporterFactory defaultReporterFactory ) { File reportsDirectory = defaultReporterFactory.getReportsDirectory(); File dumpFile = new File( reportsDirectory, creationDate + ".dumpstream" ); DumpFileUtils.dumpException( t, msg, dumpFile ); } synchronized void dumpException( Throwable t, DefaultReporterFactory defaultRepo rterFactory ) { dumpException( t, null, defaultReporterFactory ); } synchronized void dumpText( String msg, DefaultReporterFactory defaultReporterFactory ) { File reportsDirectory = defaultReporterFactory.getReportsDirectory(); File dumpFile = new File( reportsDirectory, creationDate + ".dumpstream" ); DumpFileUtils.dumpText( msg, dumpFile ); } } \ No newline at end of file +package org.apache.maven.plugin.surefire.booterclient.output; + +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +import org.apache.maven.plugin.surefire.report.DefaultReporterFactory; +import org.apache.maven.surefire.util.internal.DumpFileUtils; +import java.io.File; + +final class LostCommandsDumpSingleton +{ + private static final LostCommandsDumpSingleton SINGLETON = new LostCommandsDumpSingleton(); + + private final String creationDate = DumpFileUtils.newFormattedDateFileName(); + + private LostCommandsDumpSingleton() + { + } + + static LostCommandsDumpSingleton getSingleton() + { + return SINGLETON; + } + + synchronized void dumpException( Throwable t, String msg, DefaultReporterFactory defaultReporterFactory ) + { + DumpFileUtils.dumpException( t, msg == null ? "null" : msg, newDumpFile( defaultReporterFactory ) ); + } + + synchronized void dumpException( Throwable t, DefaultReporterFactory defaultReporterFactory ) + { + DumpFileUtils.dumpException( t, newDumpFile( defaultReporterFactory ) ); + } + + synchronized void dumpText( String msg, DefaultReporterFactory defaultReporterFactory ) + { + DumpFileUtils.dumpText( msg == null ? "null" : msg, newDumpFile( defaultReporterFactory ) ); + } + + private File newDumpFile( DefaultReporterFactory defaultReporterFactory ) + { + File reportsDirectory = defaultReporterFactory.getReportsDirectory(); + return new File( reportsDirectory, creationDate + ".dumpstream" ); + } +} http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/output/ThreadedStreamConsumer.java ---------------------------------------------------------------------- diff --git a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/output/ThreadedStreamConsumer.java b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/output/ThreadedStreamConsumer.java index 3f1abd8..ebf3edb 100644 --- a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/output/ThreadedStreamConsumer.java +++ b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/output/ThreadedStreamConsumer.java @@ -60,24 +60,35 @@ public final class ThreadedStreamConsumer this.target = target; } + /** + * Calls {@link ForkClient#consumeLine(String)} throwing {@link RuntimeException}. Even if {@link ForkClient} + * is not fault-tolerant, this method MUST be fault-tolerant except for {@link InterruptedException}.<p/> + * This Thread is interrupted by {@link #close() closing the consumer}.<p/> + * If {@link org.apache.maven.plugin.surefire.report.ConsoleOutputFileReporter#writeTestOutput} throws + * {@link java.io.IOException} this method MUST NOT interrupt reading the events from forked JVM; otherwise + * we can simply loose events like acquire-next-test which means that {@link ForkClient} hangs on waiting + * for old test to complete and therefore the plugin permanently in progress. + */ + @SuppressWarnings( "checkstyle:stringliteralequalitycheck" ) public void run() { - try + String item = null; + do { - String item = queue.take(); - //noinspection StringEquality - while ( item != POISON ) + try { - target.consumeLine( item ); item = queue.take(); + target.consumeLine( item ); } - } - catch ( Throwable t ) - { - // Think about what happens if the producer overruns us and creates an OOME. Not nice. - // Maybe limit length of blocking queue - this.throwable = t; - } + catch ( InterruptedException e ) + { + break; + } + catch ( Throwable t ) + { + throwable = t; + } + } while ( item != POISON ); } public Throwable getThrowable() http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/report/ConsoleOutputFileReporter.java ---------------------------------------------------------------------- diff --git a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/report/ConsoleOutputFileReporter.java b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/report/ConsoleOutputFileReporter.java index f9e59fe..914d684 100644 --- a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/report/ConsoleOutputFileReporter.java +++ b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/report/ConsoleOutputFileReporter.java @@ -23,6 +23,7 @@ import java.io.File; import java.io.FileOutputStream; import java.io.IOException; +import org.apache.maven.shared.utils.io.IOUtil; import org.apache.maven.surefire.report.ReportEntry; import static org.apache.maven.plugin.surefire.report.FileReporter.getReportFile; @@ -74,8 +75,12 @@ public class ConsoleOutputFileReporter } catch ( IOException e ) { + // do nothing + } + finally + { + fileOutputStream = null; } - fileOutputStream = null; } } @@ -97,6 +102,7 @@ public class ConsoleOutputFileReporter } catch ( IOException e ) { + IOUtil.close( fileOutputStream ); throw new RuntimeException( e ); } } http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/report/FileReporter.java ---------------------------------------------------------------------- diff --git a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/report/FileReporter.java b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/report/FileReporter.java index a4d8c8e..6239f77 100644 --- a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/report/FileReporter.java +++ b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/report/FileReporter.java @@ -23,7 +23,6 @@ import org.apache.maven.surefire.report.ReportEntry; import org.apache.maven.surefire.report.ReporterException; import java.io.File; -import java.io.FileWriter; import java.io.IOException; import java.io.PrintWriter; import java.util.List; @@ -60,7 +59,13 @@ public class FileReporter try { - PrintWriter writer = new PrintWriter( new FileWriter( reportFile ) ); + /** + * The implementation of constructor {@link PrintWriter(File)} + * uses {@link java.io.BufferedWriter} + * which is guaranteed by Java 1.5 Javadoc of the constructor: + * "The output will be written to the file and is buffered." + */ + PrintWriter writer = new PrintWriter( reportFile ); writer.println( "-------------------------------------------------------------------------------" ); @@ -86,6 +91,9 @@ public class FileReporter public void testSetCompleted( WrappedReportEntry report, TestSetStats testSetStats, List<String> testResults ) { + /** + * Using buffered stream internally. + */ PrintWriter writer = testSetStarting( report ); try { http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/runorder/StatisticsReporter.java ---------------------------------------------------------------------- diff --git a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/runorder/StatisticsReporter.java b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/runorder/StatisticsReporter.java index a53db02..5776cc9 100644 --- a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/runorder/StatisticsReporter.java +++ b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/runorder/StatisticsReporter.java @@ -19,9 +19,10 @@ package org.apache.maven.plugin.surefire.runorder; * under the License. */ +import org.apache.maven.surefire.report.ReportEntry; + import java.io.File; import java.io.FileNotFoundException; -import org.apache.maven.surefire.report.ReportEntry; import static org.apache.maven.plugin.surefire.runorder.RunEntryStatisticsMap.fromFile; http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/maven-surefire-common/src/test/java/org/apache/maven/surefire/report/FileReporterTest.java ---------------------------------------------------------------------- diff --git a/maven-surefire-common/src/test/java/org/apache/maven/surefire/report/FileReporterTest.java b/maven-surefire-common/src/test/java/org/apache/maven/surefire/report/FileReporterTest.java index 7c49547..076b23c 100644 --- a/maven-surefire-common/src/test/java/org/apache/maven/surefire/report/FileReporterTest.java +++ b/maven-surefire-common/src/test/java/org/apache/maven/surefire/report/FileReporterTest.java @@ -19,14 +19,14 @@ package org.apache.maven.surefire.report; * under the License. */ -import java.io.File; -import java.util.ArrayList; +import junit.framework.TestCase; import org.apache.maven.plugin.surefire.report.FileReporter; import org.apache.maven.plugin.surefire.report.ReportEntryType; import org.apache.maven.plugin.surefire.report.TestSetStats; import org.apache.maven.plugin.surefire.report.WrappedReportEntry; -import junit.framework.TestCase; +import java.io.File; +import java.util.ArrayList; public class FileReporterTest extends TestCase http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/maven-surefire-report-plugin/src/test/java/org/apache/maven/plugins/surefire/report/SurefireReportMojoTest.java ---------------------------------------------------------------------- diff --git a/maven-surefire-report-plugin/src/test/java/org/apache/maven/plugins/surefire/report/SurefireReportMojoTest.java b/maven-surefire-report-plugin/src/test/java/org/apache/maven/plugins/surefire/report/SurefireReportMojoTest.java index f138d8a..724e72d 100644 --- a/maven-surefire-report-plugin/src/test/java/org/apache/maven/plugins/surefire/report/SurefireReportMojoTest.java +++ b/maven-surefire-report-plugin/src/test/java/org/apache/maven/plugins/surefire/report/SurefireReportMojoTest.java @@ -638,7 +638,7 @@ public class SurefireReportMojoTest { outputHtml.getParentFile().mkdirs(); writer = WriterFactory.newXmlWriter( outputHtml ); - + // renderer doxia 1.6 already closed the writer renderer.generateDocument( writer, (SiteRendererSink) mojo.getSink(), context ); } finally http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-api/pom.xml ---------------------------------------------------------------------- diff --git a/surefire-api/pom.xml b/surefire-api/pom.xml index a35f983..2583972 100644 --- a/surefire-api/pom.xml +++ b/surefire-api/pom.xml @@ -33,6 +33,10 @@ <dependencies> <dependency> + <groupId>com.google.code.findbugs</groupId> + <artifactId>jsr305</artifactId> + </dependency> + <dependency> <groupId>org.apache.maven.surefire</groupId> <artifactId>surefire-logger-api</artifactId> </dependency> http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-api/src/main/java/org/apache/maven/plugin/surefire/runorder/RunEntryStatisticsMap.java ---------------------------------------------------------------------- diff --git a/surefire-api/src/main/java/org/apache/maven/plugin/surefire/runorder/RunEntryStatisticsMap.java b/surefire-api/src/main/java/org/apache/maven/plugin/surefire/runorder/RunEntryStatisticsMap.java index d47e803..eab2a81 100644 --- a/surefire-api/src/main/java/org/apache/maven/plugin/surefire/runorder/RunEntryStatisticsMap.java +++ b/surefire-api/src/main/java/org/apache/maven/plugin/surefire/runorder/RunEntryStatisticsMap.java @@ -20,12 +20,12 @@ package org.apache.maven.plugin.surefire.runorder; */ +import org.apache.maven.shared.utils.io.IOUtil; import org.apache.maven.surefire.report.ReportEntry; import java.io.BufferedReader; import java.io.File; import java.io.FileNotFoundException; -import java.io.FileOutputStream; import java.io.FileReader; import java.io.IOException; import java.io.PrintWriter; @@ -64,17 +64,19 @@ public final class RunEntryStatisticsMap { if ( file.exists() ) { + Reader reader = null; try { - return fromReader( new FileReader( file ) ); + reader = new FileReader( file ); + return fromReader( reader ); } - catch ( FileNotFoundException e ) + catch ( IOException e ) { throw new RuntimeException( e ); } - catch ( IOException e ) + finally { - throw new RuntimeException( e ); + IOUtil.close( reader ); } } else @@ -87,16 +89,11 @@ public final class RunEntryStatisticsMap throws IOException { Map<String, RunEntryStatistics> result = new HashMap<String, RunEntryStatistics>(); - BufferedReader bufferedReader = new BufferedReader( fileReader ); - String line = bufferedReader.readLine(); - while ( line != null ) + BufferedReader reader = new BufferedReader( fileReader ); + for ( String line = reader.readLine(); line != null && !line.startsWith( "#" ); line = reader.readLine() ) { - if ( !line.startsWith( "#" ) ) - { - final RunEntryStatistics stats = fromString( line ); - result.put( stats.getTestName(), stats ); - } - line = bufferedReader.readLine(); + RunEntryStatistics stats = fromString( line ); + result.put( stats.getTestName(), stats ); } return new RunEntryStatisticsMap( result ); } @@ -104,8 +101,13 @@ public final class RunEntryStatisticsMap public void serialize( File file ) throws FileNotFoundException { - FileOutputStream fos = new FileOutputStream( file ); - PrintWriter printWriter = new PrintWriter( fos ); + /** + * The implementation of constructor {@link PrintWriter(File)} + * uses {@link java.io.BufferedWriter} + * which is guaranteed by Java 1.5 Javadoc of the constructor: + * "The output will be written to the file and is buffered." + */ + PrintWriter printWriter = new PrintWriter( file ); try { List<RunEntryStatistics> items = new ArrayList<RunEntryStatistics>( runEntryStatistics.values() ); http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-api/src/main/java/org/apache/maven/surefire/booter/CommandReader.java ---------------------------------------------------------------------- diff --git a/surefire-api/src/main/java/org/apache/maven/surefire/booter/CommandReader.java b/surefire-api/src/main/java/org/apache/maven/surefire/booter/CommandReader.java index 408e4a4..3990d46 100644 --- a/surefire-api/src/main/java/org/apache/maven/surefire/booter/CommandReader.java +++ b/surefire-api/src/main/java/org/apache/maven/surefire/booter/CommandReader.java @@ -22,11 +22,9 @@ package org.apache.maven.surefire.booter; import org.apache.maven.plugin.surefire.log.api.ConsoleLogger; import org.apache.maven.plugin.surefire.log.api.NullConsoleLogger; import org.apache.maven.surefire.testset.TestSetFailedException; -import org.apache.maven.surefire.util.internal.DumpFileUtils; import java.io.DataInputStream; import java.io.EOFException; -import java.io.File; import java.io.IOException; import java.io.PrintStream; import java.util.Iterator; @@ -38,10 +36,10 @@ import java.util.concurrent.CountDownLatch; import java.util.concurrent.Semaphore; import java.util.concurrent.atomic.AtomicReference; +import static java.lang.StrictMath.max; import static java.lang.Thread.State.NEW; import static java.lang.Thread.State.RUNNABLE; import static java.lang.Thread.State.TERMINATED; -import static java.lang.StrictMath.max; import static org.apache.maven.surefire.booter.Command.toShutdown; import static org.apache.maven.surefire.booter.ForkingRunListener.BOOTERCODE_NEXT_TEST; import static org.apache.maven.surefire.booter.MasterProcessCommand.NOOP; @@ -51,10 +49,10 @@ import static org.apache.maven.surefire.booter.MasterProcessCommand.SKIP_SINCE_N import static org.apache.maven.surefire.booter.MasterProcessCommand.TEST_SET_FINISHED; import static org.apache.maven.surefire.booter.MasterProcessCommand.decode; import static org.apache.maven.surefire.util.internal.DaemonThreadFactory.newDaemonThread; +import static org.apache.maven.surefire.util.internal.ObjectUtils.requireNonNull; import static org.apache.maven.surefire.util.internal.StringUtils.encodeStringForForkCommunication; import static org.apache.maven.surefire.util.internal.StringUtils.isBlank; import static org.apache.maven.surefire.util.internal.StringUtils.isNotBlank; -import static org.apache.maven.surefire.util.internal.ObjectUtils.requireNonNull; /** * Reader of commands coming from plugin(master) process. @@ -87,8 +85,6 @@ public final class CommandReader private volatile ConsoleLogger logger = new NullConsoleLogger(); - private volatile File dumpFile; - private CommandReader() { } @@ -103,11 +99,6 @@ public final class CommandReader return reader; } - public void setDumpFile( File dumpFile ) - { - this.dumpFile = dumpFile; - } - public CommandReader setShutdown( Shutdown shutdown ) { this.shutdown = shutdown; @@ -132,7 +123,7 @@ public final class CommandReader } catch ( InterruptedException e ) { - DumpFileUtils.dumpException( e, dumpFile ); + DumpErrorSingleton.getSingleton().dumpException( e ); throw new TestSetFailedException( e.getLocalizedMessage() ); } } @@ -386,7 +377,7 @@ public final class CommandReader if ( command == null ) { String errorMessage = "[SUREFIRE] std/in stream corrupted: first sequence not recognized"; - DumpFileUtils.dumpText( errorMessage, dumpFile ); + DumpErrorSingleton.getSingleton().dumpText( errorMessage ); logger.error( errorMessage ); break; } @@ -423,7 +414,7 @@ public final class CommandReader } catch ( EOFException e ) { - DumpFileUtils.dumpException( e, dumpFile ); + DumpErrorSingleton.getSingleton().dumpException( e ); CommandReader.this.state.set( TERMINATED ); if ( !isTestSetFinished ) @@ -434,7 +425,7 @@ public final class CommandReader } catch ( IOException e ) { - DumpFileUtils.dumpException( e, dumpFile ); + DumpErrorSingleton.getSingleton().dumpException( e ); CommandReader.this.state.set( TERMINATED ); // If #stop() method is called, reader thread is interrupted and cause is InterruptedException. http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-api/src/main/java/org/apache/maven/surefire/booter/DumpErrorSingleton.java ---------------------------------------------------------------------- diff --git a/surefire-api/src/main/java/org/apache/maven/surefire/booter/DumpErrorSingleton.java b/surefire-api/src/main/java/org/apache/maven/surefire/booter/DumpErrorSingleton.java new file mode 100644 index 0000000..5df6d59 --- /dev/null +++ b/surefire-api/src/main/java/org/apache/maven/surefire/booter/DumpErrorSingleton.java @@ -0,0 +1,99 @@ +package org.apache.maven.surefire.booter; + +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +import org.apache.maven.surefire.report.ReporterConfiguration; +import org.apache.maven.surefire.util.internal.DumpFileUtils; + +import java.io.File; + +import static org.apache.maven.surefire.util.internal.DumpFileUtils.newDumpFile; + +/** + * Dumps lost commands and caused exceptions in forked JVM. <p/> + * Fail-safe. + * + * @author <a href="mailto:tibordig...@apache.org">Tibor Digana (tibor17)</a> + * @since 2.19.2 + */ +public final class DumpErrorSingleton +{ + private static final String DUMP_FILE_EXT = ".dump"; + private static final String DUMPSTREAM_FILE_EXT = ".dumpstream"; + private static final DumpErrorSingleton SINGLETON = new DumpErrorSingleton(); + + private File dumpFile; + private File dumpStreamFile; + + private DumpErrorSingleton() + { + } + + public static DumpErrorSingleton getSingleton() + { + return SINGLETON; + } + + public synchronized void init( String dumpFileName, ReporterConfiguration configuration ) + { + dumpFile = createDumpFile( dumpFileName, configuration ); + dumpStreamFile = createDumpStreamFile( dumpFileName, configuration ); + } + + public synchronized void dumpException( Throwable t, String msg ) + { + DumpFileUtils.dumpException( t, msg == null ? "null" : msg, dumpFile ); + } + + public synchronized void dumpException( Throwable t ) + { + DumpFileUtils.dumpException( t, dumpFile ); + } + + public synchronized void dumpText( String msg ) + { + DumpFileUtils.dumpText( msg == null ? "null" : msg, dumpFile ); + } + + public synchronized void dumpStreamException( Throwable t, String msg ) + { + DumpFileUtils.dumpException( t, msg == null ? "null" : msg, dumpStreamFile ); + } + + public synchronized void dumpStreamException( Throwable t ) + { + DumpFileUtils.dumpException( t, dumpStreamFile ); + } + + public synchronized void dumpStreamText( String msg ) + { + DumpFileUtils.dumpText( msg == null ? "null" : msg, dumpStreamFile ); + } + + private File createDumpFile( String dumpFileName, ReporterConfiguration configuration ) + { + return newDumpFile( dumpFileName + DUMP_FILE_EXT, configuration ); + } + + private File createDumpStreamFile( String dumpFileName, ReporterConfiguration configuration ) + { + return newDumpFile( dumpFileName + DUMPSTREAM_FILE_EXT, configuration ); + } +} http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-api/src/main/java/org/apache/maven/surefire/booter/ForkingRunListener.java ---------------------------------------------------------------------- diff --git a/surefire-api/src/main/java/org/apache/maven/surefire/booter/ForkingRunListener.java b/surefire-api/src/main/java/org/apache/maven/surefire/booter/ForkingRunListener.java index 282c4d4..aa0dadd 100644 --- a/surefire-api/src/main/java/org/apache/maven/surefire/booter/ForkingRunListener.java +++ b/surefire-api/src/main/java/org/apache/maven/surefire/booter/ForkingRunListener.java @@ -19,10 +19,6 @@ package org.apache.maven.surefire.booter; * under the License. */ -import java.io.PrintStream; -import java.util.Enumeration; -import java.util.Properties; - import org.apache.maven.plugin.surefire.log.api.ConsoleLogger; import org.apache.maven.plugin.surefire.log.api.ConsoleLoggerUtils; import org.apache.maven.surefire.report.ConsoleOutputReceiver; @@ -33,6 +29,10 @@ import org.apache.maven.surefire.report.SafeThrowable; import org.apache.maven.surefire.report.SimpleReportEntry; import org.apache.maven.surefire.report.StackTraceWriter; +import java.io.PrintStream; +import java.util.Enumeration; +import java.util.Properties; + import static java.lang.Integer.toHexString; import static java.nio.charset.Charset.defaultCharset; import static org.apache.maven.surefire.util.internal.StringUtils.encodeStringForForkCommunication; @@ -206,6 +206,13 @@ public class ForkingRunListener synchronized ( target ) // See notes about synchronization/thread safety in class javadoc { target.write( encodeBytes, 0, encodeBytes.length ); + if ( target.checkError() ) + { + // We MUST NOT throw any exception from this method; otherwise we are in loop and CPU goes up: + // ForkingRunListener -> Exception -> JUnit Notifier and RunListener -> ForkingRunListener -> Exception + DumpErrorSingleton.getSingleton() + .dumpStreamText( "Unexpected IOException with stream: " + new String( buf, off, len ) ); + } } } @@ -268,6 +275,12 @@ public class ForkingRunListener synchronized ( target ) // See notes about synchronization/thread safety in class javadoc { target.write( encodeBytes, 0, encodeBytes.length ); + if ( target.checkError() ) + { + // We MUST NOT throw any exception from this method; otherwise we are in loop and CPU goes up: + // ForkingRunListener -> Exception -> JUnit Notifier and RunListener -> ForkingRunListener -> Exception + DumpErrorSingleton.getSingleton().dumpStreamText( "Unexpected IOException: " + string ); + } } } http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-api/src/main/java/org/apache/maven/surefire/booter/MasterProcessCommand.java ---------------------------------------------------------------------- diff --git a/surefire-api/src/main/java/org/apache/maven/surefire/booter/MasterProcessCommand.java b/surefire-api/src/main/java/org/apache/maven/surefire/booter/MasterProcessCommand.java index a53a046..a75aa83 100644 --- a/surefire-api/src/main/java/org/apache/maven/surefire/booter/MasterProcessCommand.java +++ b/surefire-api/src/main/java/org/apache/maven/surefire/booter/MasterProcessCommand.java @@ -22,15 +22,14 @@ package org.apache.maven.surefire.booter; import org.apache.maven.surefire.util.internal.StringUtils; import java.io.DataInputStream; -import java.io.EOFException; import java.io.IOException; import java.io.UnsupportedEncodingException; import java.nio.charset.Charset; +import static java.lang.String.format; +import static org.apache.maven.surefire.util.internal.ObjectUtils.requireNonNull; import static org.apache.maven.surefire.util.internal.StringUtils.FORK_STREAM_CHARSET_NAME; import static org.apache.maven.surefire.util.internal.StringUtils.encodeStringForForkCommunication; -import static org.apache.maven.surefire.util.internal.ObjectUtils.requireNonNull; -import static java.lang.String.format; /** * Commands which are sent from plugin to the forked jvm. @@ -124,14 +123,8 @@ public enum MasterProcessCommand int dataLength = is.readInt(); if ( dataLength > 0 ) { - byte[] buffer = new byte[dataLength]; - int read = 0; - int total = 0; - do - { - total += read; - read = is.read( buffer, total, dataLength - total ); - } while ( read > 0 ); + byte[] buffer = new byte[ dataLength ]; + is.readFully( buffer ); if ( command.getDataType() == Void.class ) { @@ -140,17 +133,6 @@ public enum MasterProcessCommand command, dataLength ) ); } - if ( total != dataLength ) - { - if ( read == -1 ) - { - throw new EOFException( "stream closed" ); - } - - throw new IOException( format( "%s read %d out of %d bytes", - MasterProcessCommand.class, total, dataLength ) ); - } - String data = command.toDataTypeAsString( buffer ); return new Command( command, data ); } http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-booter/src/main/java/org/apache/maven/surefire/booter/ForkedBooter.java ---------------------------------------------------------------------- diff --git a/surefire-booter/src/main/java/org/apache/maven/surefire/booter/ForkedBooter.java b/surefire-booter/src/main/java/org/apache/maven/surefire/booter/ForkedBooter.java index 29047f2..b76df2f 100644 --- a/surefire-booter/src/main/java/org/apache/maven/surefire/booter/ForkedBooter.java +++ b/surefire-booter/src/main/java/org/apache/maven/surefire/booter/ForkedBooter.java @@ -54,8 +54,6 @@ import static org.apache.maven.surefire.booter.Shutdown.KILL; import static org.apache.maven.surefire.booter.SystemPropertyManager.setSystemProperties; import static org.apache.maven.surefire.util.ReflectionUtils.instantiateOneArg; import static org.apache.maven.surefire.util.internal.DaemonThreadFactory.newDaemonThreadFactory; -import static org.apache.maven.surefire.util.internal.DumpFileUtils.dumpException; -import static org.apache.maven.surefire.util.internal.DumpFileUtils.newDumpFile; import static org.apache.maven.surefire.util.internal.StringUtils.encodeStringForForkCommunication; /** @@ -73,8 +71,6 @@ public final class ForkedBooter private static final long DEFAULT_SYSTEM_EXIT_TIMEOUT_IN_SECONDS = 30; private static final long PING_TIMEOUT_IN_SECONDS = 20; private static final ScheduledExecutorService JVM_TERMINATOR = createJvmTerminator(); - private static final String DUMP_FILE_EXT = ".dump"; - private static final String DUMPSTREAM_FILE_EXT = ".dumpstream"; private static volatile long systemExitTimeoutInSeconds = DEFAULT_SYSTEM_EXIT_TIMEOUT_IN_SECONDS; @@ -89,7 +85,6 @@ public final class ForkedBooter final CommandReader reader = startupMasterProcessReader(); final ScheduledFuture<?> pingScheduler = listenToShutdownCommands( reader ); final PrintStream originalOut = out; - File dumpFile = null; try { final String tmpDir = args[0]; @@ -105,9 +100,7 @@ public final class ForkedBooter } final ProviderConfiguration providerConfiguration = booterDeserializer.deserialize(); - - dumpFile = createDumpFile( dumpFileName, providerConfiguration ); - reader.setDumpFile( createDumpstreamFile( dumpFileName, providerConfiguration ) ); + DumpErrorSingleton.getSingleton().init( dumpFileName, providerConfiguration.getReporterConfiguration() ); final StartupConfiguration startupConfiguration = booterDeserializer.getProviderConfiguration(); systemExitTimeoutInSeconds = @@ -145,7 +138,7 @@ public final class ForkedBooter } catch ( InvocationTargetException t ) { - dumpException( t, dumpFile ); + DumpErrorSingleton.getSingleton().dumpException( t ); StackTraceWriter stackTraceWriter = new LegacyPojoStackTraceWriter( "test subsystem", "no method", t.getTargetException() ); StringBuilder stringBuilder = new StringBuilder(); @@ -154,7 +147,7 @@ public final class ForkedBooter } catch ( Throwable t ) { - dumpException( t, dumpFile ); + DumpErrorSingleton.getSingleton().dumpException( t ); StackTraceWriter stackTraceWriter = new LegacyPojoStackTraceWriter( "test subsystem", "no method", t ); StringBuilder stringBuilder = new StringBuilder(); encode( stringBuilder, stackTraceWriter, false ); @@ -168,7 +161,7 @@ public final class ForkedBooter } catch ( Throwable t ) { - dumpException( t, dumpFile ); + DumpErrorSingleton.getSingleton().dumpException( t ); // Just throwing does getMessage() and a local trace - we want to call printStackTrace for a full trace // noinspection UseOfSystemOutOrSystemErr t.printStackTrace( err ); @@ -354,14 +347,4 @@ public final class ForkedBooter File surefirePropertiesFile = new File( tmpDir, propFileName ); return surefirePropertiesFile.exists() ? new FileInputStream( surefirePropertiesFile ) : null; } - - private static File createDumpFile( String dumpFileName, ProviderConfiguration providerConfiguration ) - { - return newDumpFile( dumpFileName + DUMP_FILE_EXT, providerConfiguration.getReporterConfiguration() ); - } - - private static File createDumpstreamFile( String dumpFileName, ProviderConfiguration providerConfiguration ) - { - return newDumpFile( dumpFileName + DUMPSTREAM_FILE_EXT, providerConfiguration.getReporterConfiguration() ); - } } http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-booter/src/main/java/org/apache/maven/surefire/booter/SystemPropertyManager.java ---------------------------------------------------------------------- diff --git a/surefire-booter/src/main/java/org/apache/maven/surefire/booter/SystemPropertyManager.java b/surefire-booter/src/main/java/org/apache/maven/surefire/booter/SystemPropertyManager.java index 713d4fe..a80656e 100644 --- a/surefire-booter/src/main/java/org/apache/maven/surefire/booter/SystemPropertyManager.java +++ b/surefire-booter/src/main/java/org/apache/maven/surefire/booter/SystemPropertyManager.java @@ -97,6 +97,9 @@ public class SystemPropertyManager try { + /** + * See {@link Properties#store(java.io.OutputStream, String)} Javadoc - stream is flushed. + */ properties.store( out, name ); } finally http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/fixture/TestFile.java ---------------------------------------------------------------------- diff --git a/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/fixture/TestFile.java b/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/fixture/TestFile.java index 61736df..6d3d8e2 100644 --- a/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/fixture/TestFile.java +++ b/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/fixture/TestFile.java @@ -94,23 +94,35 @@ public class TestFile public String slurpFile() { + BufferedReader reader = null; try { StringBuilder sb = new StringBuilder(); - BufferedReader reader; reader = new BufferedReader( new FileReader( file ) ); for ( String line = reader.readLine(); line != null; line = reader.readLine() ) { sb.append( line ); } - reader.close(); return sb.toString(); } catch ( IOException e ) { throw new SurefireVerifierException( e ); } - + finally + { + try + { + if ( reader != null ) + { + reader.close(); + } + } + catch ( final IOException e ) + { + // Suppressed. + } + } } public String readFileToString() http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-integration-tests/src/test/resources/classpath-order/src/test/java/it/BasicTest.java ---------------------------------------------------------------------- diff --git a/surefire-integration-tests/src/test/resources/classpath-order/src/test/java/it/BasicTest.java b/surefire-integration-tests/src/test/resources/classpath-order/src/test/java/it/BasicTest.java index 739e134..f46e3be 100644 --- a/surefire-integration-tests/src/test/resources/classpath-order/src/test/java/it/BasicTest.java +++ b/surefire-integration-tests/src/test/resources/classpath-order/src/test/java/it/BasicTest.java @@ -19,43 +19,53 @@ package it; * under the License. */ -import java.io.InputStream; +import junit.framework.TestCase; + import java.io.IOException; +import java.io.InputStream; import java.util.Properties; -import junit.framework.TestCase; - public class BasicTest - extends TestCase + extends TestCase { public void testTestClassesBeforeMainClasses() + throws IOException { Properties props = getProperties( "/surefire-classpath-order.properties" ); assertEquals( "test-classes", props.getProperty( "Surefire" ) ); } public void testMainClassesBeforeDependencies() + throws IOException { Properties props = getProperties( "/surefire-report.properties" ); assertEquals( "classes", props.getProperty( "Surefire" ) ); } - private Properties getProperties(String resource) + private Properties getProperties( String resource ) + throws IOException { InputStream in = getClass().getResourceAsStream( resource ); assertNotNull( in ); try { - Properties props = new Properties(); - props.load( in ); - return props; + Properties props = new Properties(); + props.load( in ); + return props; } - catch (IOException e) + catch ( IOException e ) { - fail(e.toString()); + fail( e.toString() ); return null; } + finally + { + if ( in != null ) + { + in.close(); + } + } } } http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-integration-tests/src/test/resources/junit4-runlistener/src/test/java/runListener/FileHelper.java ---------------------------------------------------------------------- diff --git a/surefire-integration-tests/src/test/resources/junit4-runlistener/src/test/java/runListener/FileHelper.java b/surefire-integration-tests/src/test/resources/junit4-runlistener/src/test/java/runListener/FileHelper.java index 85d0a5b..0112f31 100644 --- a/surefire-integration-tests/src/test/resources/junit4-runlistener/src/test/java/runListener/FileHelper.java +++ b/surefire-integration-tests/src/test/resources/junit4-runlistener/src/test/java/runListener/FileHelper.java @@ -22,23 +22,36 @@ package runListener; import java.io.File; import java.io.FileWriter; import java.io.IOException; +import java.io.Writer; public class FileHelper { public static void writeFile( String fileName, String content ) { + Writer writer = null; try { - File target = new File( "target" ).getAbsoluteFile(); - File listenerOutput = new File( target, fileName ); - FileWriter out = new FileWriter( listenerOutput ); - out.write( content ); - out.flush(); - out.close(); + writer = new FileWriter( new File( new File( "target" ).getAbsoluteFile(), fileName ) ); + writer.write( content ); + writer.flush(); } catch ( IOException e ) { throw new RuntimeException( e ); } + finally + { + try + { + if ( writer != null ) + { + writer.close(); + } + } + catch ( final IOException e ) + { + // Suppressed. + } + } } } http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-integration-tests/src/test/resources/surefire-803-multiFailsafeExec-failureInFirst/src/test/java/org/apache/maven/surefire/test/FailingTest.java ---------------------------------------------------------------------- diff --git a/surefire-integration-tests/src/test/resources/surefire-803-multiFailsafeExec-failureInFirst/src/test/java/org/apache/maven/surefire/test/FailingTest.java b/surefire-integration-tests/src/test/resources/surefire-803-multiFailsafeExec-failureInFirst/src/test/java/org/apache/maven/surefire/test/FailingTest.java index a4d0cd3..dc651e7 100644 --- a/surefire-integration-tests/src/test/resources/surefire-803-multiFailsafeExec-failureInFirst/src/test/java/org/apache/maven/surefire/test/FailingTest.java +++ b/surefire-integration-tests/src/test/resources/surefire-803-multiFailsafeExec-failureInFirst/src/test/java/org/apache/maven/surefire/test/FailingTest.java @@ -60,25 +60,14 @@ public class FailingTest final File f = new File( "target/tests-run", getClass().getName() + ".txt" ); f.getParentFile().mkdirs(); - FileWriter w = null; - + FileWriter w = new FileWriter( f, true ); try { - w = new FileWriter( f, true ); w.write( name.getMethodName() ); } finally { - if ( w != null ) - { - try - { - w.close(); - } - catch ( final IOException e ) - { - } - } + w.close(); } } } http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-integration-tests/src/test/resources/surefire-803-multiFailsafeExec-failureInFirst/src/test/java/org/apache/maven/surefire/test/SucceedingTest.java ---------------------------------------------------------------------- diff --git a/surefire-integration-tests/src/test/resources/surefire-803-multiFailsafeExec-failureInFirst/src/test/java/org/apache/maven/surefire/test/SucceedingTest.java b/surefire-integration-tests/src/test/resources/surefire-803-multiFailsafeExec-failureInFirst/src/test/java/org/apache/maven/surefire/test/SucceedingTest.java index c9167c1..f924074 100644 --- a/surefire-integration-tests/src/test/resources/surefire-803-multiFailsafeExec-failureInFirst/src/test/java/org/apache/maven/surefire/test/SucceedingTest.java +++ b/surefire-integration-tests/src/test/resources/surefire-803-multiFailsafeExec-failureInFirst/src/test/java/org/apache/maven/surefire/test/SucceedingTest.java @@ -60,25 +60,15 @@ public class SucceedingTest final File f = new File( "target/tests-run", getClass().getName() + ".txt" ); f.getParentFile().mkdirs(); - FileWriter w = null; + FileWriter w = new FileWriter( f, true ); try { - w = new FileWriter( f, true ); w.write( name.getMethodName() ); } finally { - if ( w != null ) - { - try - { - w.close(); - } - catch ( final IOException e ) - { - } - } + w.close(); } } } http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-integration-tests/src/test/resources/test-helper-dump-pid-plugin/src/main/java/org/apache/maven/plugins/surefire/dumppid/DumpPidMojo.java ---------------------------------------------------------------------- diff --git a/surefire-integration-tests/src/test/resources/test-helper-dump-pid-plugin/src/main/java/org/apache/maven/plugins/surefire/dumppid/DumpPidMojo.java b/surefire-integration-tests/src/test/resources/test-helper-dump-pid-plugin/src/main/java/org/apache/maven/plugins/surefire/dumppid/DumpPidMojo.java index 035976b..aa44b64 100644 --- a/surefire-integration-tests/src/test/resources/test-helper-dump-pid-plugin/src/main/java/org/apache/maven/plugins/surefire/dumppid/DumpPidMojo.java +++ b/surefire-integration-tests/src/test/resources/test-helper-dump-pid-plugin/src/main/java/org/apache/maven/plugins/surefire/dumppid/DumpPidMojo.java @@ -41,30 +41,40 @@ public class DumpPidMojo public void execute() throws MojoExecutionException { - File target; + FileWriter fw = null; try { + File target = new File( targetDir, "maven.pid" ).getCanonicalFile(); getLog().info( "Dumping PID to " + targetDir ); - + if ( !targetDir.exists() ) { targetDir.mkdirs(); } - - target = new File( targetDir, "maven.pid" ).getCanonicalFile(); - - FileWriter fw = new FileWriter( target ); + fw = new FileWriter( target ); String pid = ManagementFactory.getRuntimeMXBean().getName(); fw.write( pid ); fw.flush(); - fw.close(); - + getLog().info( "Wrote " + pid + " to " + target ); - } catch ( IOException e ) { throw new MojoExecutionException( "Unable to create pid file", e ); } + finally + { + try + { + if ( fw != null ) + { + fw.close(); + } + } + catch ( final IOException e ) + { + // Suppressed. + } + } } } http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-integration-tests/src/test/resources/testng-listener-reporter/src/test/java/listenReport/FileHelper.java ---------------------------------------------------------------------- diff --git a/surefire-integration-tests/src/test/resources/testng-listener-reporter/src/test/java/listenReport/FileHelper.java b/surefire-integration-tests/src/test/resources/testng-listener-reporter/src/test/java/listenReport/FileHelper.java index 6a6688a..031b1fa 100644 --- a/surefire-integration-tests/src/test/resources/testng-listener-reporter/src/test/java/listenReport/FileHelper.java +++ b/surefire-integration-tests/src/test/resources/testng-listener-reporter/src/test/java/listenReport/FileHelper.java @@ -22,23 +22,35 @@ package listenReport; import java.io.File; import java.io.FileWriter; import java.io.IOException; +import java.io.Writer; public class FileHelper { - public static void writeFile(String fileName, String content) + public static void writeFile( String fileName, String content ) { + Writer writer = null; try { - File target = new File( "target" ).getAbsoluteFile(); - File listenerOutput = new File( target, fileName ); - FileWriter out = new FileWriter(listenerOutput); - out.write( content ); - out.flush(); - out.close(); + writer = new FileWriter( new File( new File( "target" ).getAbsoluteFile(), fileName ) ); + writer.write( content ); } catch ( IOException e ) { - throw new RuntimeException(e); + throw new RuntimeException( e ); + } + finally + { + try + { + if ( writer != null ) + { + writer.close(); + } + } + catch ( final IOException e ) + { + throw new RuntimeException( e ); + } } } } http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-integration-tests/src/test/resources/testng-objectFactory/src/test/java/testng/objectfactory/FileHelper.java ---------------------------------------------------------------------- diff --git a/surefire-integration-tests/src/test/resources/testng-objectFactory/src/test/java/testng/objectfactory/FileHelper.java b/surefire-integration-tests/src/test/resources/testng-objectFactory/src/test/java/testng/objectfactory/FileHelper.java index 4db30b6..7e2e820 100644 --- a/surefire-integration-tests/src/test/resources/testng-objectFactory/src/test/java/testng/objectfactory/FileHelper.java +++ b/surefire-integration-tests/src/test/resources/testng-objectFactory/src/test/java/testng/objectfactory/FileHelper.java @@ -3,23 +3,38 @@ package testng.objectfactory; import java.io.File; import java.io.FileWriter; import java.io.IOException; +import java.io.Writer; public class FileHelper { public static void writeFile( String fileName, String content ) { + Writer writer = null; try { - File target = new File( System.getProperty("user.dir"), "target" ).getCanonicalFile(); - File listenerOutput = new File( target, fileName ); - FileWriter out = new FileWriter( listenerOutput, true ); - out.write( content ); - out.flush(); - out.close(); + writer = new FileWriter( new File( new File( System.getProperty( "user.dir" ), + "target" ).getCanonicalFile(), fileName ), true ); + + writer.write( content ); + writer.flush(); } catch ( IOException exception ) { throw new RuntimeException( exception ); } + finally + { + try + { + if ( writer != null ) + { + writer.close(); + } + } + catch ( final IOException e ) + { + // Suppressed. + } + } } } http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/201a3134/surefire-integration-tests/src/test/resources/testng-testRunnerFactory/src/test/java/testng/testrunnerfactory/FileHelper.java ---------------------------------------------------------------------- diff --git a/surefire-integration-tests/src/test/resources/testng-testRunnerFactory/src/test/java/testng/testrunnerfactory/FileHelper.java b/surefire-integration-tests/src/test/resources/testng-testRunnerFactory/src/test/java/testng/testrunnerfactory/FileHelper.java index 4b998ed..5451dbf 100644 --- a/surefire-integration-tests/src/test/resources/testng-testRunnerFactory/src/test/java/testng/testrunnerfactory/FileHelper.java +++ b/surefire-integration-tests/src/test/resources/testng-testRunnerFactory/src/test/java/testng/testrunnerfactory/FileHelper.java @@ -8,18 +8,32 @@ public class FileHelper { public static void writeFile( String fileName, String content ) { + FileWriter out = null; try { File target = new File( System.getProperty("user.dir"), "target" ).getCanonicalFile(); File listenerOutput = new File( target, fileName ); - FileWriter out = new FileWriter( listenerOutput, true ); + out = new FileWriter( listenerOutput, true ); out.write( content ); out.flush(); - out.close(); } - catch ( IOException exception ) + catch ( IOException e ) { - throw new RuntimeException( exception ); + throw new RuntimeException( e ); + } + finally + { + if ( out != null ) + { + try + { + out.close(); + } + catch ( IOException e ) + { + throw new RuntimeException( e ); + } + } } } }