You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@maven.apache.org by kr...@apache.org on 2012/11/17 11:25:00 UTC
[2/3] git commit: [SUREFIRE-751] forkMode=onceperthread
[SUREFIRE-751] forkMode=onceperthread
Project: http://git-wip-us.apache.org/repos/asf/maven-surefire/repo
Commit: http://git-wip-us.apache.org/repos/asf/maven-surefire/commit/9c6ce9be
Tree: http://git-wip-us.apache.org/repos/asf/maven-surefire/tree/9c6ce9be
Diff: http://git-wip-us.apache.org/repos/asf/maven-surefire/diff/9c6ce9be
Branch: refs/heads/master
Commit: 9c6ce9be423219e88d6e9c777ba69eea5e831d0c
Parents: 0b27dc2
Author: agudian <an...@gmail.com>
Authored: Tue Nov 6 21:54:00 2012 +0100
Committer: Kristian Rosenvold <kr...@apache.org>
Committed: Sat Nov 17 11:15:26 2012 +0100
----------------------------------------------------------------------
.../plugin/surefire/AbstractSurefireMojo.java | 45 +++-
.../surefire/booterclient/BooterSerializer.java | 8 +-
.../surefire/booterclient/ForkConfiguration.java | 25 ++-
.../plugin/surefire/booterclient/ForkStarter.java | 172 ++++++++++++---
.../lazytestprovider/FlushReceiver.java | 7 +
.../lazytestprovider/FlushReceiverProvider.java | 5 +
.../lazytestprovider/ProcessAwareCommandline.java | 41 ++++
.../lazytestprovider/TestProvidingInputStream.java | 52 +++++
.../surefire/booterclient/output/ForkClient.java | 17 ++
...ooterDeserializerProviderConfigurationTest.java | 59 ++++--
...BooterDeserializerStartupConfigurationTest.java | 10 +-
.../booterclient/ForkConfigurationTest.java | 4 +-
pom.xml | 2 +-
.../maven/surefire/booter/ForkingRunListener.java | 3 +
.../apache/maven/surefire/util/LazyTestsToRun.java | 135 +++++++++++
.../maven/surefire/booter/BooterConstants.java | 1 +
.../maven/surefire/booter/BooterDeserializer.java | 5 +-
.../apache/maven/surefire/booter/ForkedBooter.java | 15 ++-
.../surefire/booter/ProviderConfiguration.java | 12 +-
.../org/apache/maven/surefire/its/ForkModeIT.java | 24 ++-
.../surefire/its/fixture/SurefireLauncher.java | 10 +
.../Surefire907PerThreadWithoutThreadCountIT.java | 3 +-
.../src/test/resources/fork-mode-testng/pom.xml | 1 +
.../src/test/java/forkMode/Test1.java | 5 +
.../src/test/resources/fork-mode/pom.xml | 1 +
.../fork-mode/src/test/java/forkMode/Test1.java | 7 +-
.../maven/surefire/junit/JUnit3Provider.java | 12 +-
.../maven/surefire/junit4/JUnit4Provider.java | 18 ++-
.../surefire/junitcore/JUnitCoreProvider.java | 17 +-
.../maven/surefire/junitcore/JUnitCoreWrapper.java | 23 ++-
.../surefire/testng/TestNGDirectoryTestSuite.java | 110 ++++++----
.../maven/surefire/testng/TestNGProvider.java | 12 +-
32 files changed, 722 insertions(+), 139 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/AbstractSurefireMojo.java
----------------------------------------------------------------------
diff --git a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/AbstractSurefireMojo.java b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/AbstractSurefireMojo.java
index 7d14557..3214e2f 100644
--- a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/AbstractSurefireMojo.java
+++ b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/AbstractSurefireMojo.java
@@ -29,6 +29,7 @@ import java.util.HashMap;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.Map;
+import java.util.Map.Entry;
import java.util.Properties;
import java.util.Set;
import org.apache.maven.artifact.Artifact;
@@ -327,8 +328,11 @@ public abstract class AbstractSurefireMojo
protected Boolean failIfNoTests;
/**
- * Option to specify the forking mode. Can be "never", "once", "always" or "perthread". "none" and "pertest" are also accepted
- * for backwards compatibility. "always" forks for each test-class. "perthread" will create "threadCount" parallel forks.
+ * Option to specify the forking mode. Can be "never", "once", "always", "perthread" or "onceperthread". "none" and "pertest" are also accepted
+ * for backwards compatibility. "always" forks for each test-class. "perthread" will create "threadCount" parallel forks, each executing one test-class.
+ * "onceperthread" will fork "threadCount" processes that each execute a 1/"threadCount" of all test-classes.<br/>
+ * The system properties and the "argLine" of the forked processes may contain the place holder string <code>${surefire.threadNumber}</code>,
+ * which is replaced with a fixed number for each thread, ranging from 1 to "threadCount".
*
* @since 2.1
*/
@@ -429,9 +433,9 @@ public abstract class AbstractSurefireMojo
protected String testNGArtifactName;
/**
- * (forkMode=perthread or TestNG/JUnit 4.7 provider) The attribute thread-count allows you to specify how many threads should be
- * allocated for this execution. Only makes sense to use in conjunction with the <code>parallel</code> parameter. (forkMode=perthread
- * does not support/require the <code>parallel</code> parameter)
+ * (forkMode=perthread, forkmode=onceperthread or TestNG/JUnit 4.7 provider) The attribute thread-count allows you to specify how many threads should be
+ * allocated for this execution. Only makes sense to use in conjunction with the <code>parallel</code> parameter or with forkMode=perthread
+ * or forkmode=onceperthread.
*
* @since 2.2
*/
@@ -572,6 +576,12 @@ public abstract class AbstractSurefireMojo
private Artifact surefireBooterArtifact;
private Toolchain toolchain;
+
+ /**
+ * The placeholder that is replaced by the executing thread's running number. The thread number
+ * range starts with 1
+ */
+ public static final String THREAD_NUMBER_PLACEHOLDER = "${surefire.threadNumber}";
protected abstract String getPluginName();
@@ -741,7 +751,8 @@ public abstract class AbstractSurefireMojo
final RunResult result;
if ( isForkModeNever() )
{
- effectiveProperties.copyToSystemProperties();
+ createCopyAndReplaceThreadNumPlaceholder(effectiveProperties, 1).copyToSystemProperties();
+
InPluginVMSurefireStarter surefireStarter =
createInprocessStarter( provider, classLoaderConfiguration, runOrderParameters );
result = surefireStarter.runSuitesInProcess( scanResult );
@@ -771,6 +782,18 @@ public abstract class AbstractSurefireMojo
return result;
}
+
+ public static SurefireProperties createCopyAndReplaceThreadNumPlaceholder(SurefireProperties effectiveSystemProperties, int threadNumber) {
+ SurefireProperties filteredProperties = new SurefireProperties(effectiveSystemProperties);
+ String threadNumberString = String.valueOf(threadNumber);
+ for (Entry<Object,Object> entry : effectiveSystemProperties.entrySet()) {
+ if (entry.getValue() instanceof String) {
+ filteredProperties.put(entry.getKey(), ((String)entry.getValue()).replace(THREAD_NUMBER_PLACEHOLDER, threadNumberString));
+ }
+ }
+ return filteredProperties;
+ }
+
protected void cleanupForkConfiguration( ForkConfiguration forkConfiguration )
{
if ( !getLog().isDebugEnabled() && forkConfiguration != null )
@@ -1002,7 +1025,7 @@ public abstract class AbstractSurefireMojo
return new ProviderConfiguration( directoryScannerParameters, runOrderParameters, failIfNoTests,
reporterConfiguration, testNg, testSuiteDefinition, providerProperties,
- null );
+ null, false );
}
public String getStatisticsFileName( String configurationHash )
@@ -1344,7 +1367,8 @@ public abstract class AbstractSurefireMojo
private int getEffectiveForkCount()
{
- return ( ForkConfiguration.FORK_PERTHREAD.equals( getEffectiveForkMode() ) ) ? getThreadCount() : 1;
+ return ( ForkConfiguration.FORK_PERTHREAD.equals( getEffectiveForkMode() ) ||
+ ForkConfiguration.FORK_ONCE_PERTHREAD.equals( getEffectiveForkMode() ) ) ? getThreadCount() : 1;
}
private String getEffectiveDebugForkedProcess()
@@ -1728,9 +1752,10 @@ public abstract class AbstractSurefireMojo
void ensureThreadCountWithPerThread()
throws MojoFailureException
{
- if ( ForkConfiguration.FORK_PERTHREAD.equals( getEffectiveForkMode() ) && getThreadCount() < 1 )
+ if ( ( ForkConfiguration.FORK_PERTHREAD.equals( getEffectiveForkMode() ) ||
+ ForkConfiguration.FORK_ONCE_PERTHREAD.equals( getEffectiveForkMode() )) && getThreadCount() < 1 )
{
- throw new MojoFailureException( "Fork mode perthread requires a thread count" );
+ throw new MojoFailureException( "Fork modes perthread and onceperthread require a thread count" );
}
}
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/BooterSerializer.java
----------------------------------------------------------------------
diff --git a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/BooterSerializer.java b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/BooterSerializer.java
index c4f2c16..5b1dcbb 100644
--- a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/BooterSerializer.java
+++ b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/BooterSerializer.java
@@ -21,7 +21,9 @@ package org.apache.maven.plugin.surefire.booterclient;
import java.io.File;
import java.io.IOException;
+import java.util.List;
import java.util.Properties;
+
import org.apache.maven.surefire.booter.BooterConstants;
import org.apache.maven.surefire.booter.ClassLoaderConfiguration;
import org.apache.maven.surefire.booter.KeyValueSource;
@@ -66,7 +68,7 @@ class BooterSerializer
DOes not modify sourceProperties
*/
public File serialize(KeyValueSource sourceProperties, ProviderConfiguration booterConfiguration, StartupConfiguration providerConfiguration,
- Object testSet)
+ Object testSet, boolean readTestsFromInStream)
throws IOException
{
@@ -82,7 +84,9 @@ class BooterSerializer
properties.setProperty( BooterConstants.TESTARTIFACT_CLASSIFIER, testNg.getClassifier() );
}
- properties.setProperty( BooterConstants.FORKTESTSET, getTypeEncoded( testSet ) );
+ properties.setProperty( BooterConstants.FORKTESTSET_PREFER_TESTS_FROM_IN_STREAM, Boolean.valueOf( readTestsFromInStream ) );
+ properties.setProperty( BooterConstants.FORKTESTSET, getTypeEncoded( testSet ) );
+
TestRequest testSuiteDefinition = booterConfiguration.getTestSuiteDefinition();
if ( testSuiteDefinition != null )
{
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/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 451af02..fef053a 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
@@ -27,6 +27,9 @@ import java.util.Map;
import java.util.jar.JarEntry;
import java.util.jar.JarOutputStream;
import java.util.jar.Manifest;
+
+import org.apache.maven.plugin.surefire.AbstractSurefireMojo;
+import org.apache.maven.plugin.surefire.booterclient.lazytestprovider.ProcessAwareCommandline;
import org.apache.maven.plugin.surefire.util.Relocator;
import org.apache.maven.shared.utils.StringUtils;
import org.apache.maven.shared.utils.cli.Commandline;
@@ -52,6 +55,8 @@ public class ForkConfiguration
public static final String FORK_NEVER = "never";
public static final String FORK_PERTHREAD = "perthread";
+
+ public static final String FORK_ONCE_PERTHREAD = "onceperthread";
private final int forkCount;
@@ -102,7 +107,8 @@ public class ForkConfiguration
return FORK_NEVER;
}
else if ( forkMode.equals( FORK_NEVER ) || forkMode.equals( FORK_ONCE ) ||
- forkMode.equals( FORK_ALWAYS ) || forkMode.equals( FORK_PERTHREAD ) )
+ forkMode.equals( FORK_ALWAYS ) || forkMode.equals( FORK_PERTHREAD ) ||
+ forkMode.equals( FORK_ONCE_PERTHREAD ))
{
return forkMode;
}
@@ -117,27 +123,28 @@ public class ForkConfiguration
* @param classPath cla the classpath arguments
* @param classpathConfiguration the classpath configuration
* @param shadefire true if running shadefire
+ * @param threadNumber the thread number, to be the replacement in the argLine
* @return A commandline
* @throws org.apache.maven.surefire.booter.SurefireBooterForkException
* when unable to perform the fork
*/
- public Commandline createCommandLine( List<String> classPath, ClassLoaderConfiguration classpathConfiguration,
- boolean shadefire )
+ public ProcessAwareCommandline createCommandLine( List<String> classPath, ClassLoaderConfiguration classpathConfiguration,
+ boolean shadefire, int threadNumber )
throws SurefireBooterForkException
{
- return createCommandLine( classPath, classpathConfiguration.isManifestOnlyJarRequestedAndUsable(), shadefire );
+ return createCommandLine( classPath, classpathConfiguration.isManifestOnlyJarRequestedAndUsable(), shadefire, threadNumber );
}
- public Commandline createCommandLine( List<String> classPath, boolean useJar, boolean shadefire )
+ public ProcessAwareCommandline createCommandLine( List<String> classPath, boolean useJar, boolean shadefire, int threadNumber )
throws SurefireBooterForkException
{
- Commandline cli = new Commandline();
+ ProcessAwareCommandline cli = new ProcessAwareCommandline();
cli.setExecutable( jvmExecutable );
if ( argLine != null )
{
- cli.createArg().setLine( stripNewLines( argLine ) );
+ cli.createArg().setLine( replaceThreadNumberPlaceholder(stripNewLines( argLine ), threadNumber) );
}
if ( environmentVariables != null )
@@ -186,6 +193,10 @@ public class ForkConfiguration
return cli;
}
+ private String replaceThreadNumberPlaceholder(String argLine, int threadNumber) {
+ return argLine.replace(AbstractSurefireMojo.THREAD_NUMBER_PLACEHOLDER, String.valueOf(threadNumber));
+ }
+
/**
* Create a jar with just a manifest containing a Main-Class entry for BooterConfiguration and a Class-Path entry
* for all classpath elements.
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/ForkStarter.java
----------------------------------------------------------------------
diff --git a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/ForkStarter.java b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/ForkStarter.java
index 7a7b4bc..6c135b3 100644
--- a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/ForkStarter.java
+++ b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/ForkStarter.java
@@ -23,24 +23,31 @@ import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Iterator;
+import java.util.List;
import java.util.Properties;
+import java.util.Queue;
+import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.Callable;
+import java.util.concurrent.ConcurrentLinkedQueue;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Future;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
+import java.util.concurrent.atomic.AtomicInteger;
+import org.apache.maven.plugin.surefire.AbstractSurefireMojo;
import org.apache.maven.plugin.surefire.CommonReflector;
import org.apache.maven.plugin.surefire.StartupReportConfiguration;
import org.apache.maven.plugin.surefire.SurefireProperties;
+import org.apache.maven.plugin.surefire.booterclient.lazytestprovider.ProcessAwareCommandline;
+import org.apache.maven.plugin.surefire.booterclient.lazytestprovider.TestProvidingInputStream;
import org.apache.maven.plugin.surefire.booterclient.output.ForkClient;
import org.apache.maven.plugin.surefire.booterclient.output.ThreadedStreamConsumer;
import org.apache.maven.plugin.surefire.report.DefaultReporterFactory;
import org.apache.maven.shared.utils.cli.CommandLineException;
import org.apache.maven.shared.utils.cli.CommandLineTimeOutException;
import org.apache.maven.shared.utils.cli.CommandLineUtils;
-import org.apache.maven.shared.utils.cli.Commandline;
import org.apache.maven.surefire.booter.Classpath;
import org.apache.maven.surefire.booter.ClasspathConfiguration;
import org.apache.maven.surefire.booter.KeyValueSource;
@@ -52,9 +59,9 @@ import org.apache.maven.surefire.booter.SurefireBooterForkException;
import org.apache.maven.surefire.booter.SurefireExecutionException;
import org.apache.maven.surefire.booter.SystemPropertyManager;
import org.apache.maven.surefire.providerapi.SurefireProvider;
-import org.apache.maven.surefire.report.RunStatistics;
import org.apache.maven.surefire.suite.RunResult;
import org.apache.maven.surefire.util.DefaultScanResult;
+import org.codehaus.plexus.util.CollectionUtils;
/**
@@ -87,6 +94,17 @@ public class ForkStarter
private static volatile int systemPropertiesFileCounter = 0;
+ private final ThreadLocal<Integer> threadNumber = new ThreadLocal<Integer>()
+ {
+ private final AtomicInteger nextThreadNumber = new AtomicInteger( 1 );
+
+ @Override
+ protected Integer initialValue()
+ {
+ return nextThreadNumber.getAndIncrement();
+ }
+ };
+
public ForkStarter( ProviderConfiguration providerConfiguration, StartupConfiguration startupConfiguration,
ForkConfiguration forkConfiguration, int forkedProcessTimeoutInSeconds,
@@ -113,17 +131,21 @@ public class ForkStarter
{
final ForkClient forkClient =
new ForkClient( fileReporterFactory, startupReportConfiguration.getTestVmSystemProperties() );
- result = fork( null, new PropertiesWrapper( providerProperties ), forkClient,
- fileReporterFactory.getGlobalRunStatistics(), effectiveSystemProperties );
+ result =
+ fork( null, new PropertiesWrapper( providerProperties ), forkClient, effectiveSystemProperties, 1,
+ null );
}
else if ( ForkConfiguration.FORK_ALWAYS.equals( requestedForkMode ) )
{
- result = runSuitesForkPerTestSet( providerProperties, effectiveSystemProperties, 1 );
+ result = runSuitesForkPerTestSet( effectiveSystemProperties, 1 );
}
else if ( ForkConfiguration.FORK_PERTHREAD.equals( requestedForkMode ) )
{
- result = runSuitesForkPerTestSet( providerProperties, effectiveSystemProperties,
- forkConfiguration.getForkCount() );
+ result = runSuitesForkPerTestSet( effectiveSystemProperties, forkConfiguration.getForkCount() );
+ }
+ else if ( ForkConfiguration.FORK_ONCE_PERTHREAD.equals( requestedForkMode ) )
+ {
+ result = runSuitesForkOncePerThread( effectiveSystemProperties, forkConfiguration.getForkCount() );
}
else
{
@@ -137,8 +159,85 @@ public class ForkStarter
return result;
}
- private RunResult runSuitesForkPerTestSet( final Properties properties,
- final SurefireProperties effectiveSystemProperties, int forkCount )
+ private RunResult runSuitesForkOncePerThread( final SurefireProperties effectiveSystemProperties, int forkCount )
+ throws SurefireBooterForkException
+ {
+
+ ArrayList<Future<RunResult>> results = new ArrayList<Future<RunResult>>( forkCount );
+ ExecutorService executorService = new ThreadPoolExecutor( forkCount, forkCount, 60, TimeUnit.SECONDS,
+ new ArrayBlockingQueue<Runnable>( forkCount ) );
+
+ try
+ {
+ // Ask to the executorService to run all tasks
+ RunResult globalResult = new RunResult( 0, 0, 0, 0 );
+
+ List<Class<?>> suites = CollectionUtils.iteratorToList( getSuitesIterator() );
+ final Queue<String> messageQueue = new ConcurrentLinkedQueue<String>();
+ for ( Class<?> clazz : suites )
+ {
+ messageQueue.add( clazz.getName() );
+ }
+
+ for ( int threadNum = 0; threadNum < forkCount && threadNum < suites.size(); threadNum++ )
+ {
+ final int finalThreadNumber = threadNum + 1;
+
+ Callable<RunResult> pf = new Callable<RunResult>()
+ {
+ public RunResult call()
+ throws Exception
+ {
+ TestProvidingInputStream testProvidingInputStream =
+ new TestProvidingInputStream( messageQueue );
+
+ ForkClient forkClient =
+ new ForkClient( fileReporterFactory, startupReportConfiguration.getTestVmSystemProperties(),
+ testProvidingInputStream );
+
+ return fork( null, new PropertiesWrapper( providerConfiguration.getProviderProperties() ),
+ forkClient, effectiveSystemProperties, finalThreadNumber,
+ testProvidingInputStream );
+ }
+ };
+
+ results.add( executorService.submit( pf ) );
+ }
+
+ for ( Future<RunResult> result : results )
+ {
+ try
+ {
+ RunResult cur = result.get();
+ if ( cur != null )
+ {
+ globalResult = globalResult.aggregate( cur );
+ }
+ else
+ {
+ throw new SurefireBooterForkException( "No results for " + result.toString() );
+ }
+ }
+ catch ( InterruptedException e )
+ {
+ throw new SurefireBooterForkException( "Interrupted", e );
+ }
+ catch ( ExecutionException e )
+ {
+ throw new SurefireBooterForkException( "ExecutionException", e );
+ }
+ }
+ return globalResult;
+
+ }
+ finally
+ {
+ closeExecutor( executorService );
+ }
+
+ }
+
+ private RunResult runSuitesForkPerTestSet( final SurefireProperties effectiveSystemProperties, final int forkCount )
throws SurefireBooterForkException
{
@@ -150,19 +249,27 @@ public class ForkStarter
{
// Ask to the executorService to run all tasks
RunResult globalResult = new RunResult( 0, 0, 0, 0 );
- final Iterator suites = getSuitesIterator();
+ final Iterator<Class<?>> suites = getSuitesIterator();
while ( suites.hasNext() )
{
final Object testSet = suites.next();
- final ForkClient forkClient =
- new ForkClient( fileReporterFactory, startupReportConfiguration.getTestVmSystemProperties() );
Callable<RunResult> pf = new Callable<RunResult>()
{
public RunResult call()
throws Exception
{
- return fork( testSet, new PropertiesWrapper( properties ), forkClient,
- fileReporterFactory.getGlobalRunStatistics(), effectiveSystemProperties );
+ int thisThreadsThreadNumber = threadNumber.get();
+ if ( thisThreadsThreadNumber > forkCount )
+ {
+ // this would be a bug in the ThreadPoolExecutor
+ throw new IllegalStateException(
+ "More threads than " + forkCount + " have been created by the ThreadPoolExecutor." );
+ }
+
+ ForkClient forkClient = new ForkClient( fileReporterFactory,
+ startupReportConfiguration.getTestVmSystemProperties() );
+ return fork( testSet, new PropertiesWrapper( providerConfiguration.getProviderProperties() ),
+ forkClient, effectiveSystemProperties, thisThreadsThreadNumber, null );
}
};
results.add( executorService.submit( pf ) );
@@ -217,9 +324,9 @@ public class ForkStarter
}
}
-
private RunResult fork( Object testSet, KeyValueSource providerProperties, ForkClient forkClient,
- RunStatistics globalRunStatistics, SurefireProperties effectiveSystemProperties )
+ SurefireProperties effectiveSystemProperties, int threadNumber,
+ TestProvidingInputStream testProvidingInputStream )
throws SurefireBooterForkException
{
File surefireProperties;
@@ -229,14 +336,18 @@ public class ForkStarter
BooterSerializer booterSerializer = new BooterSerializer( forkConfiguration );
surefireProperties =
- booterSerializer.serialize( providerProperties, providerConfiguration, startupConfiguration, testSet );
+ booterSerializer.serialize( providerProperties, providerConfiguration, startupConfiguration, testSet,
+ null != testProvidingInputStream );
if ( effectiveSystemProperties != null )
{
- systPropsFile = SystemPropertyManager.writePropertiesFile( effectiveSystemProperties,
- forkConfiguration.getTempDirectory(),
- "surefire_" + systemPropertiesFileCounter++,
- forkConfiguration.isDebug() );
+ SurefireProperties filteredProperties =
+ AbstractSurefireMojo.createCopyAndReplaceThreadNumPlaceholder( effectiveSystemProperties,
+ threadNumber );
+ systPropsFile =
+ SystemPropertyManager.writePropertiesFile( filteredProperties, forkConfiguration.getTempDirectory(),
+ "surefire_" + systemPropertiesFileCounter++,
+ forkConfiguration.isDebug() );
}
}
catch ( IOException e )
@@ -254,10 +365,15 @@ public class ForkStarter
// Surefire-booter if !useSystemClassLoader
Classpath bootClasspath = Classpath.join( bootClasspathConfiguration, additionlClassPathUrls );
- @SuppressWarnings( "unchecked" ) Commandline cli =
+ @SuppressWarnings( "unchecked" ) ProcessAwareCommandline cli =
forkConfiguration.createCommandLine( bootClasspath.getClassPath(),
startupConfiguration.getClassLoaderConfiguration(),
- startupConfiguration.isShadefire() );
+ startupConfiguration.isShadefire(), threadNumber );
+
+ if ( testProvidingInputStream != null )
+ {
+ testProvidingInputStream.setFlushReceiverProvider( cli );
+ }
cli.createArg().setFile( surefireProperties );
@@ -279,7 +395,8 @@ public class ForkStarter
{
final int timeout = forkedProcessTimeoutInSeconds > 0 ? forkedProcessTimeoutInSeconds : 0;
final int result =
- CommandLineUtils.executeCommandLine( cli, threadedStreamConsumer, threadedStreamConsumer, timeout );
+ CommandLineUtils.executeCommandLine( cli, testProvidingInputStream, threadedStreamConsumer,
+ threadedStreamConsumer, timeout );
if ( result != RunResult.SUCCESS )
{
throw new SurefireBooterForkException( "Error occurred in starting fork, check output in log" );
@@ -299,17 +416,18 @@ public class ForkStarter
finally
{
threadedStreamConsumer.close();
- forkClient.close(runResult == RunResult.Timeout);
+ forkClient.close( runResult == RunResult.Timeout );
if ( runResult == null )
{
- runResult = globalRunStatistics.getRunResult();
+ runResult = fileReporterFactory.getGlobalRunStatistics().getRunResult();
}
}
return runResult;
}
- private Iterator getSuitesIterator()
+ @SuppressWarnings( "unchecked" )
+ private Iterator<Class<?>> getSuitesIterator()
throws SurefireBooterForkException
{
try
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/FlushReceiver.java
----------------------------------------------------------------------
diff --git a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/FlushReceiver.java b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/FlushReceiver.java
new file mode 100644
index 0000000..5269d7a
--- /dev/null
+++ b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/FlushReceiver.java
@@ -0,0 +1,7 @@
+package org.apache.maven.plugin.surefire.booterclient.lazytestprovider;
+
+import java.io.IOException;
+
+public interface FlushReceiver {
+ void flush() throws IOException;
+}
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/FlushReceiverProvider.java
----------------------------------------------------------------------
diff --git a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/FlushReceiverProvider.java b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/FlushReceiverProvider.java
new file mode 100644
index 0000000..f285a66
--- /dev/null
+++ b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/FlushReceiverProvider.java
@@ -0,0 +1,5 @@
+package org.apache.maven.plugin.surefire.booterclient.lazytestprovider;
+
+public interface FlushReceiverProvider {
+ FlushReceiver getFlushReceiver();
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/ProcessAwareCommandline.java
----------------------------------------------------------------------
diff --git a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/ProcessAwareCommandline.java b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/ProcessAwareCommandline.java
new file mode 100644
index 0000000..5182107
--- /dev/null
+++ b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/ProcessAwareCommandline.java
@@ -0,0 +1,41 @@
+package org.apache.maven.plugin.surefire.booterclient.lazytestprovider;
+
+import java.io.IOException;
+import java.io.OutputStream;
+
+import org.apache.maven.shared.utils.cli.CommandLineException;
+import org.apache.maven.shared.utils.cli.Commandline;
+
+
+
+public class ProcessAwareCommandline extends Commandline implements FlushReceiverProvider {
+ private final class OutputStreamFlushReceiver implements FlushReceiver {
+ private final OutputStream outputStream;
+
+ private OutputStreamFlushReceiver(OutputStream outputStream) {
+ this.outputStream = outputStream;
+ }
+
+ public void flush() throws IOException {
+ outputStream.flush();
+ }
+ }
+
+ private FlushReceiver flushReceiver;
+
+ @Override
+ public Process execute() throws CommandLineException {
+ Process process = super.execute();
+
+ if (process.getOutputStream() != null) {
+ flushReceiver = new OutputStreamFlushReceiver(process.getOutputStream());
+ }
+
+ return process;
+ }
+
+ public FlushReceiver getFlushReceiver() {
+ return flushReceiver;
+ }
+
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/TestProvidingInputStream.java
----------------------------------------------------------------------
diff --git a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/TestProvidingInputStream.java b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/TestProvidingInputStream.java
new file mode 100644
index 0000000..a4e899d
--- /dev/null
+++ b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/lazytestprovider/TestProvidingInputStream.java
@@ -0,0 +1,52 @@
+package org.apache.maven.plugin.surefire.booterclient.lazytestprovider;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.util.Queue;
+import java.util.concurrent.Semaphore;
+
+public class TestProvidingInputStream extends InputStream {
+ private final Queue<String> testItemQueue;
+ private byte[] currentBuffer;
+ private int currentPos;
+ private Semaphore semaphore = new Semaphore(0);
+ private FlushReceiverProvider flushReceiverProvider;
+
+ public TestProvidingInputStream(Queue<String> testItemQueue) {
+ this.testItemQueue = testItemQueue;
+ }
+
+ public void setFlushReceiverProvider(FlushReceiverProvider flushReceiverProvider) {
+ this.flushReceiverProvider = flushReceiverProvider;
+ }
+
+ @Override
+ public synchronized int read() throws IOException {
+ if (null == currentBuffer) {
+ if (null != flushReceiverProvider && null != flushReceiverProvider.getFlushReceiver()) {
+ flushReceiverProvider.getFlushReceiver().flush();
+ }
+
+ semaphore.acquireUninterruptibly();
+
+ String currentElement = testItemQueue.poll();
+ if (null != currentElement) {
+ currentBuffer = currentElement.getBytes();
+ currentPos = 0;
+ } else {
+ return -1;
+ }
+ }
+
+ if (currentPos < currentBuffer.length) {
+ return (currentBuffer[currentPos++] & 0xff);
+ } else {
+ currentBuffer = null;
+ return ('\n' & 0xff);
+ }
+ }
+
+ public void provideNewTest() {
+ semaphore.release();
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/output/ForkClient.java
----------------------------------------------------------------------
diff --git a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/output/ForkClient.java b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/output/ForkClient.java
index 7559954..fa7d141 100644
--- a/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/output/ForkClient.java
+++ b/maven-surefire-common/src/main/java/org/apache/maven/plugin/surefire/booterclient/output/ForkClient.java
@@ -28,6 +28,8 @@ import java.util.HashMap;
import java.util.Map;
import java.util.Properties;
import java.util.StringTokenizer;
+
+import org.apache.maven.plugin.surefire.booterclient.lazytestprovider.TestProvidingInputStream;
import org.apache.maven.plugin.surefire.report.DefaultReporterFactory;
import org.apache.maven.shared.utils.cli.StreamConsumer;
import org.apache.maven.surefire.booter.ForkingRunListener;
@@ -36,6 +38,7 @@ import org.apache.maven.surefire.report.ConsoleLogger;
import org.apache.maven.surefire.report.ConsoleOutputReceiver;
import org.apache.maven.surefire.report.ReportEntry;
import org.apache.maven.surefire.report.ReporterException;
+import org.apache.maven.surefire.report.ReporterFactory;
import org.apache.maven.surefire.report.RunListener;
import org.apache.maven.surefire.report.StackTraceWriter;
import org.apache.maven.surefire.util.NestedRuntimeException;
@@ -49,7 +52,9 @@ import org.apache.maven.surefire.util.internal.StringUtils;
public class ForkClient
implements StreamConsumer
{
+
private final DefaultReporterFactory providerReporterFactory;
+ private final TestProvidingInputStream testProvidingInputStream;
private final Map<Integer, RunListener> testSetReporters =
Collections.synchronizedMap( new HashMap<Integer, RunListener>() );
@@ -60,8 +65,14 @@ public class ForkClient
public ForkClient( DefaultReporterFactory providerReporterFactory, Properties testVmSystemProperties )
{
+ this(providerReporterFactory, testVmSystemProperties, null);
+ }
+
+ public ForkClient( DefaultReporterFactory providerReporterFactory, Properties testVmSystemProperties, TestProvidingInputStream testProvidingInputStream )
+ {
this.providerReporterFactory = providerReporterFactory;
this.testVmSystemProperties = testVmSystemProperties;
+ this.testProvidingInputStream = testProvidingInputStream;
}
public void consumeLine( String s )
@@ -134,6 +145,12 @@ public class ForkClient
case ForkingRunListener.BOOTERCODE_CONSOLE:
getOrCreateConsoleLogger( channelNumber ).info( createConsoleMessage( remaining ) );
break;
+ case ForkingRunListener.BOOTERCODE_NEXT_TEST:
+ if (null != testProvidingInputStream)
+ {
+ testProvidingInputStream.provideNewTest();
+ }
+ break;
case ForkingRunListener.BOOTERCODE_BYE:
saidGoodBye = true;
break;
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/maven-surefire-common/src/test/java/org/apache/maven/plugin/surefire/booterclient/BooterDeserializerProviderConfigurationTest.java
----------------------------------------------------------------------
diff --git a/maven-surefire-common/src/test/java/org/apache/maven/plugin/surefire/booterclient/BooterDeserializerProviderConfigurationTest.java b/maven-surefire-common/src/test/java/org/apache/maven/plugin/surefire/booterclient/BooterDeserializerProviderConfigurationTest.java
index b7e1eba..509929d 100644
--- a/maven-surefire-common/src/test/java/org/apache/maven/plugin/surefire/booterclient/BooterDeserializerProviderConfigurationTest.java
+++ b/maven-surefire-common/src/test/java/org/apache/maven/plugin/surefire/booterclient/BooterDeserializerProviderConfigurationTest.java
@@ -27,13 +27,16 @@ import java.util.Arrays;
import java.util.Collections;
import java.util.List;
import java.util.Properties;
+
+import junit.framework.Assert;
+import junit.framework.TestCase;
+
import org.apache.maven.surefire.booter.BooterDeserializer;
import org.apache.maven.surefire.booter.ClassLoaderConfiguration;
import org.apache.maven.surefire.booter.ClasspathConfiguration;
import org.apache.maven.surefire.booter.PropertiesWrapper;
import org.apache.maven.surefire.booter.ProviderConfiguration;
import org.apache.maven.surefire.booter.StartupConfiguration;
-import org.apache.maven.surefire.booter.SystemPropertyManager;
import org.apache.maven.surefire.booter.TypeEncodedValue;
import org.apache.maven.surefire.report.ReporterConfiguration;
import org.apache.maven.surefire.testset.DirectoryScannerParameters;
@@ -42,9 +45,6 @@ import org.apache.maven.surefire.testset.TestArtifactInfo;
import org.apache.maven.surefire.testset.TestRequest;
import org.apache.maven.surefire.util.RunOrder;
-import junit.framework.Assert;
-import junit.framework.TestCase;
-
/**
* Performs roundtrip testing of serialization/deserialization of the ProviderConfiguration
*
@@ -55,7 +55,7 @@ public class BooterDeserializerProviderConfigurationTest
{
public static final TypeEncodedValue aTestTyped = new TypeEncodedValue( String.class.getName(), "aTest" );
-
+
private final String aUserRequestedTest = "aUserRequestedTest";
private static ClassLoaderConfiguration getForkConfiguration()
@@ -79,7 +79,7 @@ public class BooterDeserializerProviderConfigurationTest
ClassLoaderConfiguration forkConfiguration = getForkConfiguration();
final StartupConfiguration testStartupConfiguration = getTestStartupConfiguration( forkConfiguration );
ProviderConfiguration providerConfiguration = getReloadedProviderConfiguration();
- ProviderConfiguration read = saveAndReload( providerConfiguration, testStartupConfiguration );
+ ProviderConfiguration read = saveAndReload( providerConfiguration, testStartupConfiguration, false );
Assert.assertEquals( aDir, read.getBaseDir() );
Assert.assertEquals( includes.get( 0 ), read.getIncludes().get( 0 ) );
@@ -95,10 +95,10 @@ public class BooterDeserializerProviderConfigurationTest
DirectoryScannerParameters directoryScannerParameters = getDirectoryScannerParametersWithoutSpecificTests();
ClassLoaderConfiguration forkConfiguration = getForkConfiguration();
- ProviderConfiguration providerConfiguration = getTestProviderConfiguration( directoryScannerParameters );
+ ProviderConfiguration providerConfiguration = getTestProviderConfiguration( directoryScannerParameters, false );
final StartupConfiguration testProviderConfiguration = getTestStartupConfiguration( forkConfiguration );
- ProviderConfiguration reloaded = saveAndReload( providerConfiguration, testProviderConfiguration );
+ ProviderConfiguration reloaded = saveAndReload( providerConfiguration, testProviderConfiguration, false );
assertTrue( reloaded.getReporterConfiguration().isTrimStackTrace().booleanValue() );
assertNotNull( reloaded.getReporterConfiguration().getReportsDirectory() );
@@ -134,6 +134,15 @@ public class BooterDeserializerProviderConfigurationTest
Assert.assertEquals( aTestTyped, reloaded.getTestForFork() );
}
+
+ public void testTestForForkWithMultipleFiles()
+ throws IOException
+ {
+ final ProviderConfiguration reloaded = getReloadedProviderConfigurationForReadFromInStream();
+ Assert.assertNull( reloaded.getTestForFork() );
+ Assert.assertTrue( reloaded.isReadTestsFromInStream() );
+
+ }
public void testFailIfNoTests()
throws IOException
@@ -143,14 +152,26 @@ public class BooterDeserializerProviderConfigurationTest
}
+ private ProviderConfiguration getReloadedProviderConfigurationForReadFromInStream()
+ throws IOException
+ {
+ return getReloadedProviderConfiguration(true);
+ }
+
private ProviderConfiguration getReloadedProviderConfiguration()
+ throws IOException
+ {
+ return getReloadedProviderConfiguration(false);
+ }
+
+ private ProviderConfiguration getReloadedProviderConfiguration(boolean readTestsFromInStream)
throws IOException
{
DirectoryScannerParameters directoryScannerParameters = getDirectoryScannerParametersWithoutSpecificTests();
ClassLoaderConfiguration forkConfiguration = getForkConfiguration();
- ProviderConfiguration booterConfiguration = getTestProviderConfiguration( directoryScannerParameters );
+ ProviderConfiguration booterConfiguration = getTestProviderConfiguration( directoryScannerParameters, readTestsFromInStream );
final StartupConfiguration testProviderConfiguration = getTestStartupConfiguration( forkConfiguration );
- return saveAndReload( booterConfiguration, testProviderConfiguration );
+ return saveAndReload( booterConfiguration, testProviderConfiguration, readTestsFromInStream );
}
private DirectoryScannerParameters getDirectoryScannerParametersWithoutSpecificTests()
@@ -168,19 +189,27 @@ public class BooterDeserializerProviderConfigurationTest
}
private ProviderConfiguration saveAndReload( ProviderConfiguration booterConfiguration,
- StartupConfiguration testProviderConfiguration )
+ StartupConfiguration testProviderConfiguration, boolean readTestsFromInStream )
throws IOException
{
final ForkConfiguration forkConfiguration = ForkConfigurationTest.getForkConfiguration( null, null );
PropertiesWrapper props = new PropertiesWrapper( new Properties());
BooterSerializer booterSerializer = new BooterSerializer( forkConfiguration );
- String aTest = "aTest";
- final File propsTest = booterSerializer.serialize( props, booterConfiguration, testProviderConfiguration, aTest);
+ Object test;
+ if (readTestsFromInStream)
+ {
+ test = null;
+ }
+ else
+ {
+ test = "aTest";
+ }
+ final File propsTest = booterSerializer.serialize( props, booterConfiguration, testProviderConfiguration, test, readTestsFromInStream);
BooterDeserializer booterDeserializer = new BooterDeserializer( new FileInputStream( propsTest ) );
return booterDeserializer.deserialize();
}
- private ProviderConfiguration getTestProviderConfiguration( DirectoryScannerParameters directoryScannerParameters )
+ private ProviderConfiguration getTestProviderConfiguration( DirectoryScannerParameters directoryScannerParameters, boolean readTestsFromInStream )
{
File cwd = new File( "." );
@@ -192,7 +221,7 @@ public class BooterDeserializerProviderConfigurationTest
RunOrderParameters runOrderParameters = new RunOrderParameters( RunOrder.DEFAULT, null );
return new ProviderConfiguration( directoryScannerParameters, runOrderParameters, true, reporterConfiguration,
new TestArtifactInfo( "5.0", "ABC" ), testSuiteDefinition, new Properties(),
- aTestTyped );
+ aTestTyped, readTestsFromInStream );
}
private StartupConfiguration getTestStartupConfiguration( ClassLoaderConfiguration classLoaderConfiguration )
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/maven-surefire-common/src/test/java/org/apache/maven/plugin/surefire/booterclient/BooterDeserializerStartupConfigurationTest.java
----------------------------------------------------------------------
diff --git a/maven-surefire-common/src/test/java/org/apache/maven/plugin/surefire/booterclient/BooterDeserializerStartupConfigurationTest.java b/maven-surefire-common/src/test/java/org/apache/maven/plugin/surefire/booterclient/BooterDeserializerStartupConfigurationTest.java
index bc9085a..d72621d 100644
--- a/maven-surefire-common/src/test/java/org/apache/maven/plugin/surefire/booterclient/BooterDeserializerStartupConfigurationTest.java
+++ b/maven-surefire-common/src/test/java/org/apache/maven/plugin/surefire/booterclient/BooterDeserializerStartupConfigurationTest.java
@@ -25,6 +25,9 @@ import java.io.IOException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Properties;
+
+import junit.framework.TestCase;
+
import org.apache.maven.surefire.booter.BooterDeserializer;
import org.apache.maven.surefire.booter.ClassLoaderConfiguration;
import org.apache.maven.surefire.booter.Classpath;
@@ -32,7 +35,6 @@ import org.apache.maven.surefire.booter.ClasspathConfiguration;
import org.apache.maven.surefire.booter.PropertiesWrapper;
import org.apache.maven.surefire.booter.ProviderConfiguration;
import org.apache.maven.surefire.booter.StartupConfiguration;
-import org.apache.maven.surefire.booter.SystemPropertyManager;
import org.apache.maven.surefire.report.ReporterConfiguration;
import org.apache.maven.surefire.testset.DirectoryScannerParameters;
import org.apache.maven.surefire.testset.RunOrderParameters;
@@ -40,8 +42,6 @@ import org.apache.maven.surefire.testset.TestArtifactInfo;
import org.apache.maven.surefire.testset.TestRequest;
import org.apache.maven.surefire.util.RunOrder;
-import junit.framework.TestCase;
-
/**
* Performs roundtrip testing of serialization/deserialization of The StartupConfiguration
*
@@ -130,7 +130,7 @@ public class BooterDeserializerStartupConfigurationTest
PropertiesWrapper props = new PropertiesWrapper( new Properties());
BooterSerializer booterSerializer = new BooterSerializer( forkConfiguration );
String aTest = "aTest";
- final File propsTest = booterSerializer.serialize( props, getProviderConfiguration(), startupConfiguration, aTest);
+ final File propsTest = booterSerializer.serialize( props, getProviderConfiguration(), startupConfiguration, aTest, false );
BooterDeserializer booterDeserializer = new BooterDeserializer( new FileInputStream( propsTest ) );
return booterDeserializer.getProviderConfiguration();
}
@@ -152,7 +152,7 @@ public class BooterDeserializerStartupConfigurationTest
RunOrderParameters runOrderParameters = new RunOrderParameters( RunOrder.DEFAULT, null );
return new ProviderConfiguration( directoryScannerParameters, runOrderParameters, true, reporterConfiguration,
new TestArtifactInfo( "5.0", "ABC" ), testSuiteDefinition, new Properties(),
- BooterDeserializerProviderConfigurationTest.aTestTyped );
+ BooterDeserializerProviderConfigurationTest.aTestTyped, true );
}
private StartupConfiguration getTestStartupConfiguration( ClassLoaderConfiguration classLoaderConfiguration )
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/maven-surefire-common/src/test/java/org/apache/maven/plugin/surefire/booterclient/ForkConfigurationTest.java
----------------------------------------------------------------------
diff --git a/maven-surefire-common/src/test/java/org/apache/maven/plugin/surefire/booterclient/ForkConfigurationTest.java b/maven-surefire-common/src/test/java/org/apache/maven/plugin/surefire/booterclient/ForkConfigurationTest.java
index ce44f23..6ec931e 100644
--- a/maven-surefire-common/src/test/java/org/apache/maven/plugin/surefire/booterclient/ForkConfigurationTest.java
+++ b/maven-surefire-common/src/test/java/org/apache/maven/plugin/surefire/booterclient/ForkConfigurationTest.java
@@ -41,7 +41,7 @@ public class ForkConfigurationTest
File cpElement = getTempClasspathFile();
Commandline cli =
- config.createCommandLine( Collections.singletonList( cpElement.getAbsolutePath() ), true, false );
+ config.createCommandLine( Collections.singletonList( cpElement.getAbsolutePath() ), true, false, 1 );
String line = StringUtils.join( cli.getCommandline(), " " );
assertTrue( line.contains( "-jar" ) );
@@ -56,7 +56,7 @@ public class ForkConfigurationTest
final Commandline commandLine =
forkConfiguration.createCommandLine( Collections.singletonList( cpElement.getAbsolutePath() ), false,
- false );
+ false, 1 );
assertTrue( commandLine.toString().contains( "abc def" ) );
}
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/pom.xml
----------------------------------------------------------------------
diff --git a/pom.xml b/pom.xml
index 11776ba..2eb2c3c 100644
--- a/pom.xml
+++ b/pom.xml
@@ -222,7 +222,7 @@
<dependency>
<groupId>org.apache.maven.shared</groupId>
<artifactId>maven-shared-utils</artifactId>
- <version>0.1</version>
+ <version>0.2-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>jmock</groupId>
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/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 b3283e3..e5c8ac3 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
@@ -22,6 +22,7 @@ package org.apache.maven.surefire.booter;
import java.io.PrintStream;
import java.util.Enumeration;
import java.util.Properties;
+
import org.apache.maven.surefire.report.ConsoleLogger;
import org.apache.maven.surefire.report.ConsoleOutputReceiver;
import org.apache.maven.surefire.report.ReportEntry;
@@ -75,6 +76,8 @@ public class ForkingRunListener
public static final byte BOOTERCODE_SYSPROPS = (byte) 'I';
+ public static final byte BOOTERCODE_NEXT_TEST = (byte) 'N';
+
public static final byte BOOTERCODE_BYE = (byte) 'Z';
private final PrintStream target;
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/surefire-api/src/main/java/org/apache/maven/surefire/util/LazyTestsToRun.java
----------------------------------------------------------------------
diff --git a/surefire-api/src/main/java/org/apache/maven/surefire/util/LazyTestsToRun.java b/surefire-api/src/main/java/org/apache/maven/surefire/util/LazyTestsToRun.java
new file mode 100644
index 0000000..dabe1ae
--- /dev/null
+++ b/surefire-api/src/main/java/org/apache/maven/surefire/util/LazyTestsToRun.java
@@ -0,0 +1,135 @@
+/**
+ *
+ */
+package org.apache.maven.surefire.util;
+
+import java.io.BufferedReader;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.io.PrintStream;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+
+import org.apache.maven.surefire.booter.ForkingRunListener;
+
+/**
+ * A variant of TestsToRun that is provided with test class names asynchronously
+ * from an {@link InputStream} (e.g. {@code System.in}). The method
+ * {@link #iterator()} returns an Iterator that blocks on calls to
+ * {@link Iterator#hasNext()} until new classes are available, or no more
+ * classes will be available.
+ * <p/>
+ * The methods {@link #getLocatedClasses()} and {@link #size()} will throw an
+ * {@link UnsupportedOperationException}.
+ *
+ * @author Andreas Gudian
+ *
+ */
+public class LazyTestsToRun extends TestsToRun {
+ private List workQueue = new ArrayList();
+ private BufferedReader inputReader;
+ private boolean streamClosed = false;
+ private ClassLoader testClassLoader;
+ private PrintStream originalOutStream;
+
+ public LazyTestsToRun(InputStream testSource, ClassLoader testClassLoader, PrintStream originalOutStream) {
+ super(Collections.emptyList());
+
+ this.testClassLoader = testClassLoader;
+ this.originalOutStream = originalOutStream;
+
+ inputReader = new BufferedReader(new InputStreamReader(testSource));
+ }
+
+ protected void addWorkItem(String className) {
+ synchronized (workQueue) {
+ workQueue.add(ReflectionUtils.loadClass(testClassLoader, className));
+ }
+ }
+
+ protected void requestNextTest() {
+ StringBuffer sb = new StringBuffer();
+ sb.append((char) ForkingRunListener.BOOTERCODE_NEXT_TEST).append(",0,want more!\n");
+ originalOutStream.print(sb.toString());
+ }
+
+ private class BlockingIterator implements Iterator {
+ private int lastPos = -1;
+
+ public boolean hasNext() {
+ int nextPos = lastPos + 1;
+ synchronized (workQueue) {
+ if (workQueue.size() > nextPos) {
+ return true;
+ } else {
+ if (needsToWaitForInput(nextPos)) {
+ requestNextTest();
+
+ String nextClassName;
+ try {
+ nextClassName = inputReader.readLine();
+ } catch (IOException e) {
+ streamClosed = true;
+ return false;
+ }
+
+ if (null == nextClassName) {
+ streamClosed = true;
+ } else {
+ addWorkItem(nextClassName);
+ }
+ }
+
+ return (workQueue.size() > nextPos);
+ }
+ }
+ }
+
+ private boolean needsToWaitForInput(int nextPos) {
+ return workQueue.size() == nextPos && !streamClosed;
+ }
+
+ public Object next() {
+ synchronized (workQueue) {
+ return workQueue.get(++lastPos);
+ }
+ }
+
+ public void remove() {
+ throw new UnsupportedOperationException();
+ }
+
+ }
+
+ public Iterator iterator() {
+ return new BlockingIterator();
+ }
+
+ /**
+ * Unsupported. Use {@link #iterator()} instead.
+ */
+ public int size() {
+ throw new UnsupportedOperationException("use method iterator()");
+ }
+
+ /**
+ * Unsupported. Use {@link #iterator()} instead.
+ */
+ public Class[] getLocatedClasses() {
+ throw new UnsupportedOperationException("use method iterator()");
+ }
+
+ public String toString() {
+ StringBuffer sb = new StringBuffer("LazyTestsToRun ");
+ synchronized (workQueue) {
+ sb.append("(more items expected: ").append(!streamClosed).append("): ");
+ sb.append(workQueue);
+ }
+
+ return sb.toString();
+ }
+
+}
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/surefire-booter/src/main/java/org/apache/maven/surefire/booter/BooterConstants.java
----------------------------------------------------------------------
diff --git a/surefire-booter/src/main/java/org/apache/maven/surefire/booter/BooterConstants.java b/surefire-booter/src/main/java/org/apache/maven/surefire/booter/BooterConstants.java
index 375bf68..430ea9c 100644
--- a/surefire-booter/src/main/java/org/apache/maven/surefire/booter/BooterConstants.java
+++ b/surefire-booter/src/main/java/org/apache/maven/surefire/booter/BooterConstants.java
@@ -46,4 +46,5 @@ public interface BooterConstants
String TEST_SUITE_XML_FILES = "testSuiteXmlFiles";
String PROVIDER_CONFIGURATION = "providerConfiguration";
String FORKTESTSET = "forkTestSet";
+ String FORKTESTSET_PREFER_TESTS_FROM_IN_STREAM = "preferTestsFromInStream";
}
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/surefire-booter/src/main/java/org/apache/maven/surefire/booter/BooterDeserializer.java
----------------------------------------------------------------------
diff --git a/surefire-booter/src/main/java/org/apache/maven/surefire/booter/BooterDeserializer.java b/surefire-booter/src/main/java/org/apache/maven/surefire/booter/BooterDeserializer.java
index af03c1c..85e4c93 100644
--- a/surefire-booter/src/main/java/org/apache/maven/surefire/booter/BooterDeserializer.java
+++ b/surefire-booter/src/main/java/org/apache/maven/surefire/booter/BooterDeserializer.java
@@ -61,7 +61,10 @@ public class BooterDeserializer
final File reportsDirectory = new File( properties.getProperty( REPORTSDIRECTORY ) );
final String testNgVersion = properties.getProperty( TESTARTIFACT_VERSION );
final String testArtifactClassifier = properties.getProperty( TESTARTIFACT_CLASSIFIER );
+
final TypeEncodedValue typeEncodedTestForFork = properties.getTypeEncodedValue( FORKTESTSET );
+ final boolean preferTestsFromInStream = properties.getBooleanProperty( FORKTESTSET_PREFER_TESTS_FROM_IN_STREAM );
+
final String requestedTest = properties.getProperty( REQUESTEDTEST );
final String requestedTestMethod = properties.getProperty( REQUESTEDTESTMETHOD );
final File sourceDirectory = properties.getFileProperty( SOURCE_DIRECTORY );
@@ -90,7 +93,7 @@ public class BooterDeserializer
return new ProviderConfiguration( dirScannerParams, runOrderParameters,
properties.getBooleanProperty( FAILIFNOTESTS ), reporterConfiguration, testNg,
- testSuiteDefinition, properties.getProperties(), typeEncodedTestForFork );
+ testSuiteDefinition, properties.getProperties(), typeEncodedTestForFork, preferTestsFromInStream );
}
public StartupConfiguration getProviderConfiguration()
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/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 938755c..2e8f812 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
@@ -23,7 +23,9 @@ import java.io.File;
import java.io.FileInputStream;
import java.io.InputStream;
import java.io.PrintStream;
+
import org.apache.maven.surefire.suite.RunResult;
+import org.apache.maven.surefire.util.LazyTestsToRun;
/**
* The part of the booter that is unique to a forked vm.
@@ -64,6 +66,7 @@ public class ForkedBooter
final StartupConfiguration startupConfiguration = booterDeserializer.getProviderConfiguration();
TypeEncodedValue forkedTestSet = providerConfiguration.getTestForFork();
+ boolean readTestsFromInputStream = providerConfiguration.isReadTestsFromInStream();
final ClasspathConfiguration classpathConfiguration = startupConfiguration.getClasspathConfiguration();
final ClassLoader testClassLoader = classpathConfiguration.createForkingTestClassLoader(
@@ -71,7 +74,17 @@ public class ForkedBooter
startupConfiguration.writeSurefireTestClasspathProperty();
- Object testSet = forkedTestSet != null ? forkedTestSet.getDecodedValue( testClassLoader ) : null;
+ Object testSet;
+ if (forkedTestSet != null) {
+ testSet = forkedTestSet.getDecodedValue( testClassLoader );
+ }
+ else if (readTestsFromInputStream) {
+ testSet = new LazyTestsToRun(System.in, testClassLoader, originalOut);
+ }
+ else {
+ testSet = null;
+ }
+
runSuitesInProcess( testSet, testClassLoader, startupConfiguration, providerConfiguration, originalOut );
// Say bye.
originalOut.println( "Z,0,BYE!" );
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/surefire-booter/src/main/java/org/apache/maven/surefire/booter/ProviderConfiguration.java
----------------------------------------------------------------------
diff --git a/surefire-booter/src/main/java/org/apache/maven/surefire/booter/ProviderConfiguration.java b/surefire-booter/src/main/java/org/apache/maven/surefire/booter/ProviderConfiguration.java
index bc1dc7f..23535ad 100644
--- a/surefire-booter/src/main/java/org/apache/maven/surefire/booter/ProviderConfiguration.java
+++ b/surefire-booter/src/main/java/org/apache/maven/surefire/booter/ProviderConfiguration.java
@@ -64,12 +64,14 @@ public class ProviderConfiguration
private final boolean failIfNoTests;
private final TypeEncodedValue forkTestSet;
+
+ private final boolean readTestsFromInStream;
public ProviderConfiguration( DirectoryScannerParameters directoryScannerParameters,
RunOrderParameters runOrderParameters, boolean failIfNoTests,
ReporterConfiguration reporterConfiguration, TestArtifactInfo testArtifact,
TestRequest testSuiteDefinition, Properties providerProperties,
- TypeEncodedValue typeEncodedTestSet )
+ TypeEncodedValue typeEncodedTestSet, boolean readTestsFromInStream)
{
this.runOrderParameters = runOrderParameters;
this.providerProperties = providerProperties;
@@ -79,6 +81,7 @@ public class ProviderConfiguration
this.dirScannerParams = directoryScannerParameters;
this.failIfNoTests = failIfNoTests;
this.forkTestSet = typeEncodedTestSet;
+ this.readTestsFromInStream = readTestsFromInStream;
}
@@ -133,9 +136,14 @@ public class ProviderConfiguration
{
return forkTestSet;
}
-
+
public RunOrderParameters getRunOrderParameters()
{
return runOrderParameters;
}
+
+
+ public boolean isReadTestsFromInStream() {
+ return readTestsFromInStream;
+ }
}
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/ForkModeIT.java
----------------------------------------------------------------------
diff --git a/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/ForkModeIT.java b/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/ForkModeIT.java
index 158ad85..8653106 100644
--- a/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/ForkModeIT.java
+++ b/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/ForkModeIT.java
@@ -19,6 +19,10 @@ package org.apache.maven.surefire.its;
* under the License.
*/
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.Set;
+
import org.apache.maven.surefire.its.fixture.OutputValidator;
import org.apache.maven.surefire.its.fixture.SurefireIntegrationTestCase;
import org.apache.maven.surefire.its.fixture.SurefireLauncher;
@@ -55,8 +59,25 @@ public class ForkModeIT
String[] pids = doTest( unpack( getProject() ).forkMode( "none" ) );
assertSamePids( pids );
}
+
+ public void testForkModeOncePerThreadSingleThread()
+ {
+ String[] pids = doTest( unpack( getProject() ).forkOncePerThread().threadCount(1) );
+ assertSamePids( pids );
+ }
+
+ public void testForkModeOncePerThreadTwoThreads()
+ {
+ String[] pids = doTest( unpack( getProject() ).forkOncePerThread().threadCount(2) );
+ assertDifferentPids( pids, 2 );
+ }
+
+ private void assertDifferentPids(String[] pids, int numOfDifferentPids) {
+ Set<String> pidSet = new HashSet<String>(Arrays.asList(pids));
+ assertEquals( "number of different pids is not as expected", numOfDifferentPids, pidSet.size() );
+ }
- public void testForkModeOnce()
+ public void testForkModeOnce()
{
String[] pids = doTest( unpack( getProject() ).forkOnce() );
// DGF It would be nice to assert that "once" was different
@@ -92,6 +113,7 @@ public class ForkModeIT
private String[] doTest( SurefireLauncher forkMode )
{
+ forkMode.addD( "testProperty", "testValue_${surefire.threadNumber}" );
final OutputValidator outputValidator = forkMode.executeTest();
outputValidator.verifyErrorFreeLog().assertTestSuiteResults( 3, 0, 0, 0 );
String[] pids = new String[3];
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/fixture/SurefireLauncher.java
----------------------------------------------------------------------
diff --git a/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/fixture/SurefireLauncher.java b/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/fixture/SurefireLauncher.java
index d6fc2e8..552e8b4 100755
--- a/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/fixture/SurefireLauncher.java
+++ b/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/fixture/SurefireLauncher.java
@@ -384,6 +384,16 @@ public class SurefireLauncher
return forkMode( "perthread" );
}
+ public SurefireLauncher forkOncePerThread()
+ {
+ return forkMode( "onceperthread" );
+ }
+
+ public SurefireLauncher threadCount(int threadCount)
+ {
+ return addGoal( "-DthreadCount=" + threadCount );
+ }
+
public SurefireLauncher forkMode( String forkMode )
{
return addGoal( "-DforkMode=" + forkMode );
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/jiras/Surefire907PerThreadWithoutThreadCountIT.java
----------------------------------------------------------------------
diff --git a/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/jiras/Surefire907PerThreadWithoutThreadCountIT.java b/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/jiras/Surefire907PerThreadWithoutThreadCountIT.java
index 43ecef4..577b8a5 100755
--- a/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/jiras/Surefire907PerThreadWithoutThreadCountIT.java
+++ b/surefire-integration-tests/src/test/java/org/apache/maven/surefire/its/jiras/Surefire907PerThreadWithoutThreadCountIT.java
@@ -19,7 +19,6 @@ package org.apache.maven.surefire.its.jiras;
*/
import org.apache.maven.surefire.its.fixture.OutputValidator;
import org.apache.maven.surefire.its.fixture.SurefireJUnit4IntegrationTestCase;
-import org.apache.maven.surefire.its.fixture.SurefireLauncher;
import org.junit.Test;
@@ -30,7 +29,7 @@ public class Surefire907PerThreadWithoutThreadCountIT
public void categoryAB()
{
OutputValidator validator = unpack("fork-mode").forkPerThread().executeTestWithFailure();
- validator.verifyTextInLog( "Fork mode perthread requires a thread count" );
+ validator.verifyTextInLog( "Fork modes perthread and onceperthread require a thread count" );
}
}
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/surefire-integration-tests/src/test/resources/fork-mode-testng/pom.xml
----------------------------------------------------------------------
diff --git a/surefire-integration-tests/src/test/resources/fork-mode-testng/pom.xml b/surefire-integration-tests/src/test/resources/fork-mode-testng/pom.xml
index 62593c9..25b66f0 100644
--- a/surefire-integration-tests/src/test/resources/fork-mode-testng/pom.xml
+++ b/surefire-integration-tests/src/test/resources/fork-mode-testng/pom.xml
@@ -26,6 +26,7 @@
<version>${surefire.version}</version>
<configuration>
<forkMode>${forkMode}</forkMode>
+ <threadCount>${threadCount}</threadCount>
</configuration>
</plugin>
</plugins>
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/surefire-integration-tests/src/test/resources/fork-mode-testng/src/test/java/forkMode/Test1.java
----------------------------------------------------------------------
diff --git a/surefire-integration-tests/src/test/resources/fork-mode-testng/src/test/java/forkMode/Test1.java b/surefire-integration-tests/src/test/resources/fork-mode-testng/src/test/java/forkMode/Test1.java
index ef70d3e..408550b 100644
--- a/surefire-integration-tests/src/test/resources/fork-mode-testng/src/test/java/forkMode/Test1.java
+++ b/surefire-integration-tests/src/test/resources/fork-mode-testng/src/test/java/forkMode/Test1.java
@@ -4,12 +4,15 @@ import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.lang.management.ManagementFactory;
+import java.util.Random;
import org.testng.annotations.Test;
public class Test1
{
+ private static final Random RANDOM = new Random();
+
@Test
public void test1()
throws IOException
@@ -32,6 +35,8 @@ public class Test1
// In fact, it usually contains the pid and the local host name!
String pid = ManagementFactory.getRuntimeMXBean().getName();
fw.write( pid );
+ fw.write( " " );
+ fw.write( System.getProperty( "testProperty", String.valueOf( RANDOM.nextLong() ) ) );
fw.flush();
fw.close();
}
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/surefire-integration-tests/src/test/resources/fork-mode/pom.xml
----------------------------------------------------------------------
diff --git a/surefire-integration-tests/src/test/resources/fork-mode/pom.xml b/surefire-integration-tests/src/test/resources/fork-mode/pom.xml
index 416fda9..aa37e2c 100644
--- a/surefire-integration-tests/src/test/resources/fork-mode/pom.xml
+++ b/surefire-integration-tests/src/test/resources/fork-mode/pom.xml
@@ -42,6 +42,7 @@
<version>${surefire.version}</version>
<configuration>
<forkMode>${forkMode}</forkMode>
+ <threadCount>${threadCount}</threadCount>
</configuration>
</plugin>
</plugins>
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/surefire-integration-tests/src/test/resources/fork-mode/src/test/java/forkMode/Test1.java
----------------------------------------------------------------------
diff --git a/surefire-integration-tests/src/test/resources/fork-mode/src/test/java/forkMode/Test1.java b/surefire-integration-tests/src/test/resources/fork-mode/src/test/java/forkMode/Test1.java
index 05bac14..35f746e 100644
--- a/surefire-integration-tests/src/test/resources/fork-mode/src/test/java/forkMode/Test1.java
+++ b/surefire-integration-tests/src/test/resources/fork-mode/src/test/java/forkMode/Test1.java
@@ -4,6 +4,7 @@ import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.lang.management.ManagementFactory;
+import java.util.Random;
import junit.framework.TestCase;
@@ -11,7 +12,9 @@ public class Test1
extends TestCase
{
- public void test1()
+ private static final Random RANDOM = new Random();
+
+ public void test1()
throws IOException
{
dumpPidFile( this );
@@ -32,6 +35,8 @@ public class Test1
// In fact, it usually contains the pid and the local host name!
String pid = ManagementFactory.getRuntimeMXBean().getName();
fw.write( pid );
+ fw.write( " " );
+ fw.write( System.getProperty( "testProperty", String.valueOf( RANDOM.nextLong() ) ) );
fw.flush();
fw.close();
}
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/surefire-providers/surefire-junit3/src/main/java/org/apache/maven/surefire/junit/JUnit3Provider.java
----------------------------------------------------------------------
diff --git a/surefire-providers/surefire-junit3/src/main/java/org/apache/maven/surefire/junit/JUnit3Provider.java b/surefire-providers/surefire-junit3/src/main/java/org/apache/maven/surefire/junit/JUnit3Provider.java
index ff39099..bbff4da 100644
--- a/surefire-providers/surefire-junit3/src/main/java/org/apache/maven/surefire/junit/JUnit3Provider.java
+++ b/surefire-providers/surefire-junit3/src/main/java/org/apache/maven/surefire/junit/JUnit3Provider.java
@@ -76,7 +76,17 @@ public class JUnit3Provider
{
if ( testsToRun == null )
{
- testsToRun = forkTestSet == null ? scanClassPath() : TestsToRun.fromClass( (Class<?>) forkTestSet );
+ if (forkTestSet instanceof TestsToRun)
+ {
+ testsToRun = (TestsToRun) forkTestSet;
+ }
+ else if (forkTestSet instanceof Class)
+ {
+ testsToRun = TestsToRun.fromClass( (Class<?>) forkTestSet );
+ } else
+ {
+ testsToRun = scanClassPath();
+ }
}
ReporterFactory reporterFactory = providerParameters.getReporterFactory();
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/surefire-providers/surefire-junit4/src/main/java/org/apache/maven/surefire/junit4/JUnit4Provider.java
----------------------------------------------------------------------
diff --git a/surefire-providers/surefire-junit4/src/main/java/org/apache/maven/surefire/junit4/JUnit4Provider.java b/surefire-providers/surefire-junit4/src/main/java/org/apache/maven/surefire/junit4/JUnit4Provider.java
index 28f127f..5354685 100644
--- a/surefire-providers/surefire-junit4/src/main/java/org/apache/maven/surefire/junit4/JUnit4Provider.java
+++ b/surefire-providers/surefire-junit4/src/main/java/org/apache/maven/surefire/junit4/JUnit4Provider.java
@@ -89,9 +89,19 @@ public class JUnit4Provider
{
if ( testsToRun == null )
{
- testsToRun = forkTestSet == null ? scanClassPath() : TestsToRun.fromClass( (Class<?>) forkTestSet );
+ if (forkTestSet instanceof TestsToRun)
+ {
+ testsToRun = (TestsToRun) forkTestSet;
+ }
+ else if (forkTestSet instanceof Class)
+ {
+ testsToRun = TestsToRun.fromClass( (Class) forkTestSet );
+ } else
+ {
+ testsToRun = scanClassPath();
+ }
}
-
+
upgradeCheck();
final ReporterFactory reporterFactory = providerParameters.getReporterFactory();
@@ -107,9 +117,9 @@ public class JUnit4Provider
runNotifer.fireTestRunStarted( null );
- for ( Class<?> clazz : testsToRun.getLocatedClasses() )
+ for ( Iterator<Class<?>> iter = testsToRun.iterator(); iter.hasNext(); )
{
- executeTestSet( clazz, reporter, runNotifer );
+ executeTestSet( iter.next(), reporter, runNotifer );
}
runNotifer.fireTestRunFinished( result );
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/surefire-providers/surefire-junit47/src/main/java/org/apache/maven/surefire/junitcore/JUnitCoreProvider.java
----------------------------------------------------------------------
diff --git a/surefire-providers/surefire-junit47/src/main/java/org/apache/maven/surefire/junitcore/JUnitCoreProvider.java b/surefire-providers/surefire-junit47/src/main/java/org/apache/maven/surefire/junitcore/JUnitCoreProvider.java
index 01b7c5d..afe6888 100644
--- a/surefire-providers/surefire-junit47/src/main/java/org/apache/maven/surefire/junitcore/JUnitCoreProvider.java
+++ b/surefire-providers/surefire-junit47/src/main/java/org/apache/maven/surefire/junitcore/JUnitCoreProvider.java
@@ -116,12 +116,17 @@ public class JUnitCoreProvider
if ( testsToRun == null )
{
- testsToRun = forkTestSet == null ? getSuitesAsList( filter ) : TestsToRun.fromClass( (Class) forkTestSet );
- }
-
- if ( testsToRun.size() == 0 )
- {
- filter = null;
+ if (forkTestSet instanceof TestsToRun)
+ {
+ testsToRun = (TestsToRun) forkTestSet;
+ }
+ else if (forkTestSet instanceof Class)
+ {
+ testsToRun = TestsToRun.fromClass( (Class) forkTestSet );
+ } else
+ {
+ testsToRun = getSuitesAsList( filter );
+ }
}
final Map<String, TestSet> testSetMap = new ConcurrentHashMap<String, TestSet>();
http://git-wip-us.apache.org/repos/asf/maven-surefire/blob/9c6ce9be/surefire-providers/surefire-junit47/src/main/java/org/apache/maven/surefire/junitcore/JUnitCoreWrapper.java
----------------------------------------------------------------------
diff --git a/surefire-providers/surefire-junit47/src/main/java/org/apache/maven/surefire/junitcore/JUnitCoreWrapper.java b/surefire-providers/surefire-junit47/src/main/java/org/apache/maven/surefire/junitcore/JUnitCoreWrapper.java
index 57350b9..bfd4dff 100644
--- a/surefire-providers/surefire-junit47/src/main/java/org/apache/maven/surefire/junitcore/JUnitCoreWrapper.java
+++ b/surefire-providers/surefire-junit47/src/main/java/org/apache/maven/surefire/junitcore/JUnitCoreWrapper.java
@@ -19,12 +19,13 @@ package org.apache.maven.surefire.junitcore;
* under the License.
*/
+import java.util.Iterator;
import java.util.List;
import java.util.concurrent.ExecutionException;
+
import org.apache.maven.surefire.common.junit4.JUnit4RunListener;
import org.apache.maven.surefire.testset.TestSetFailedException;
import org.apache.maven.surefire.util.TestsToRun;
-
import org.junit.runner.Computer;
import org.junit.runner.JUnitCore;
import org.junit.runner.Request;
@@ -51,16 +52,20 @@ class JUnitCoreWrapper
junitCore.addListener( runListener );
}
- Request req = Request.classes( computer, testsToRun.getLocatedClasses() );
- if ( filter != null )
- {
- req = req.filterWith( filter );
- }
-
try
{
- final Result run = junitCore.run( req );
- JUnit4RunListener.rethrowAnyTestMechanismFailures( run );
+ Iterator classIter = testsToRun.iterator();
+ while (classIter.hasNext())
+ {
+ Request req = Request.classes( computer, new Class[]{ (Class) classIter.next() });
+ if ( filter != null )
+ {
+ req = req.filterWith( filter );
+ }
+
+ final Result run = junitCore.run( req );
+ JUnit4RunListener.rethrowAnyTestMechanismFailures( run );
+ }
}
finally
{