Permalink
Browse files

Initial draft of a new examples page explaining the fork and parallel…

… options

Signed-off-by: Kristian Rosenvold <krosenvold@apache.org>
  • Loading branch information...
1 parent 12b7012 commit 44e006ace699e35a04f4aa71f49ace83e817912a @agudian agudian committed with krosenvold Jan 3, 2013
@@ -0,0 +1,161 @@
+ ------
+ Fork Options and Parallel Test Execution
+ ------
+ Andreas Gudian
+ ------
+ 2013-01-03
+ ------
+
+ ~~ 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.
+
+ ~~ NOTE: For help with the syntax of this file, see:
+ ~~ http://maven.apache.org/doxia/references/apt-format.html
+
+Fork Options and Parallel Test Execution
+
+ Choosing the right forking strategy and parallel execution settings can have
+ substantial impact on the memory requirements and the execution time of your
+ build system.
+
+ Surefire offers a variety of options to execute tests in parallel, allowing
+ you to make best use of the hardware at your disposal. But forking in
+ particular can also help keeping the memory requirements low.
+
+ This page shall give you some ideas of how you can configure the test
+ execution in a way best suitable for your environment.
+
+* Parallel Test Execution
+
+ Basically, there are two ways in Surefire to achieve parallel test execution.
+ The most obvious one is by using the <<<parallel>>> parameter. The possible
+ values depend on the test provider used. For JUnit 4.7 and onwards, this may
+ be <<<methods>>>, <<<classes>>>, or <<<both>>>.
+
+ See the example pages for {{{./junit.html#Running_tests_in_parallel}JUnit}}
+ and {{{./testng.html#Running_tests_in_parallel}TestNG}} for details.
+
+ The <extent> of the parallelism is configured using the parameters
+ <<<threadCount>>>, and optionally <<<perCoreThreadCount>>>, or
+ <<<useUnlimitedThreads>>>.
+
+ <<The important thing to remember>> with the <<<parallel>>> option is: the
+ concurrency happens within the same JVM process. That is efficient in terms of
+ memory and execution time, but you may be more vulnerable towards race
+ conditions or other unexpected and hard to reproduce behavior.
+
+ The other possibility for parallel test execution is <<<forkMode=perthread>>>.
+ It spawns up to <<<threadCount>>> new JVM processes concurrently to execute
+ the tests. The next section covers the details about this and the other
+ <<<forkMode>>> settings.
+
+* Forked Test Execution
+
+ The default setting is <<<forkMode=once>>>, which means that Surefire creates
+ one new JVM process to execute all tests in one maven module.
+
+ Using <<<forkMode=never>>> disables forking and executes the tests within
+ the main maven process. This avoids the additional startup and warm-up time
+ of your JVM, but also means that you might have to account for higher memory
+ requirements, especially PermGen.
+
+ <<<forkMode=always>>> executes each test class in its own JVM process, one
+ after another. It creates the highest level of separation for the test
+ execution, but it would probably also give you the longest execution time
+ of all the available options. Consider it as a last resort.
+
+ The most powerful setting is <<<forkMode=perthread>>>. Surefire creates up to
+ <<<threadCount>>> JVM processes to execute tests in parallel. Each process
+ executes one test at a time. The parameter <<<reuseForks>>> is used to define
+ whether the process shall terminate after each test and to create a new
+ process for the next test in line (<<<reuseForks=false>>>, the default
+ setting), or whether to reuse the processes to execute the next tests
+ (<<<reuseForks=true>>>, new since Surefire 2.13).
+
+ Please note that <<<reuseForks>>> currently only affects
+ <<<forkMode=perthread>>>.
+
+ With the <<<argLine>>> property, you can specify additional parameters to be
+ passed to the forked JVM process, such as memory settings. System property
+ variables from the main maven process are passed to the forked process as
+ well. Additionally, you can use the element <<<systemPropertyVariables>>> to
+ specify variables and values to be added to the system properties during the
+ test execution.
+
+ You can use the place holder <<<$\{surefire.threadNumber\}>>> within
+ <<<argLine>>>, or within the system properties (both those specified via
+ <<<mvn test -D...>>> and via <<<systemPropertyVariables>>>). Before executing
+ the tests, Surefire replaces that place holder by the number of the actually
+ executing process, counting from 1 to the value of <<<threadCount>>>.
+
+ For the fork modes other than <<<perthread>>>, the place holder will always be
+ replaced with <1>.
+
+ The following is an example configuration that makes use of up to three forked
+ processes that execute the tests and then terminate. A system property
+ <databaseSchema> is passed to the processes, that shall specify the database
+ schema to use during the tests. The values for that will be
+ <MY_TEST_SCHEMA_1>, <MY_TEST_SCHEMA_2>, and <MY_TEST_SCHEMA_3> for the three
+ processes.
+
++---+
+<plugins>
+[...]
+ <plugin>
+ <groupId>${project.groupId}</groupId>
+ <artifactId>${project.artifactId}</artifactId>
+ <version>${project.version}</version>
+ <configuration>
+ <forkMode>perthread</forkMode>
+ <reuseForks>true</reuseForks>
+ <threadCount>3</threadCount>
+ <argLine>-Xmx1024m -XX:MaxPermSize=256m</argLine>
+ <systemPropertyVariables>
+ <databaseSchema>MY_TEST_SCHEMA_${surefire.threadNumber}</databaseSchema>
+ </systemPropertyVariables>
+ </configuration>
+ </plugin>
+[...]
+</plugins>
++---+
+
+ Imagine you execute some tests that use a JPA context, which has a notable
+ initial startup time. By setting <<<reuseForks=true>>>, you can reuse that
+ context for consecutive tests. And as many tests tend to use and access the
+ same test data, you can avoid database locks during the concurrent execution
+ by using distinct but uniform database schemas.
+
+ Port numbers and file names are other examples of resources for which it may
+ be hard or undesired to be shared among concurrent test executions.
+
+* Combining forkMode and parallel
+
+ The modes <<<forkMode=never>>> and <<<forkMode=once>>> can be combined freely
+ with the available settings for <<<parallel>>>.
+
+ As <<<forkMode=always>>> creates a new JVM process for each test class,
+ using <<<parallel=classes>>> would have no effect. You can still use
+ <<<parallel=methods>>>, though.
+
+ When using <<<forkMode=perthread>>>, test classes are handed over to the
+ forked process one-by-one. Thus, <<<parallel=classes>>> would not change
+ anything. However, you can use <<<parallel=methods>>>: classes are executed in
+ <<<threadCount=X>>> concurrent processes, each of the processes can then use
+ the same number of <<<X>>> threads to execute the methods of one class in
+ parallel. Please note, that the option <<<perCoreThreadCount>>> only has an
+ effect on the number of threads for method-concurrency, but not on the number
+ of forked processes.
@@ -48,6 +48,7 @@
<item name="Configuring the Classpath" href="examples/configuring-classpath.html"/>
<item name="Selecting providers" href="examples/providers.html"/>
<item name="New error summary" href="newerrorsummary.html"/>
+ <item name="Fork Options and Parallel Test Execution" href="examples/fork-options-and-parallel-execution.html"/>
</menu>
</body>
</project>

0 comments on commit 44e006a

Please sign in to comment.