Skip to content

Commit c808b8d

Browse files
Merge pull request #720 from hgschmie/maven-switches
Adds two new switches to the maven test goal
2 parents 1b58afc + 3f4b698 commit c808b8d

File tree

7 files changed

+385
-3
lines changed

7 files changed

+385
-3
lines changed

docs/src/docs/asciidoc/changelog.adoc

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,8 @@
44
== Release 0.11.1
55

66
- Fix `NoClassDefFoundError` when JUnit feature is missing some dependency
7+
- Add `skipTestExecution` support to `native-maven-plugin`
8+
- Add `failNoTests` support to `native-maven-plugin`
79

810
== Release 0.11.0
911

docs/src/docs/asciidoc/end-to-end-maven-guide.adoc

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -232,6 +232,16 @@ This works similarly to `JAVA_TOOL_OPTIONS`, where the value of the environment
232232

233233
Learn more about Native Image build configuration https://www.graalvm.org/reference-manual/native-image/overview/BuildConfiguration/[on the website].
234234

235+
=== Build, but not execute native tests
236+
237+
During a transition phase, it is often useful to build tests but not execute them. This allows inspection of the generated test image without failing the build when the tests do not execute successfully.
238+
239+
If you wish to build, but not execute, the native tests, invoke Maven with the `-DskipTestExecution` switch or set the value in the plugin configuration.
240+
241+
=== Skip modules without native tests in multi-module builds
242+
243+
Multi-module projects where only some sub-modules contain native tests need to skip test execution for any module that do not contain native tests. Skip test execution for modules by setting the `<failNoTests>` configuration to `false` or providing `-DfailNoTests=false` on the command line.
244+
235245
[[gather-execution-profiles]]
236246
=== Gather Execution Profiles and Build Optimized Images
237247

docs/src/docs/asciidoc/maven-plugin.adoc

Lines changed: 82 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,18 @@ The following configuration options are available:
6161
----
6262
<skipNativeTests>true</skipNativeTests>
6363
----
64+
`<skipTestExecution>`::
65+
Skips execution of native tests. If set to true, the plugin will create the native image for the tests but will not execute the tests. This allows the creation of the native image for testing even when tests don't fully execute or tests fail. Otherwise, the build stops at the first test failure. To skip only the execution of the native image compiled tests, add:
66+
[source,xml, role="multi-language-sample"]
67+
----
68+
<skipNativeTests>true</skipNativeTests>
69+
----
70+
`<failNoTests>`::
71+
Fails the build if no tests were found. In multi-module builds, there are often modules that have no tests (for example, a documentation module ) or where tests are enabled or disabled by profiles (such as slow tests, e2e tests, etc.). This switch allows for a global configuration of the native plugin and then allows you to skip any modules where no tests are present by changing this setting to false in the sub-module. This allows such multi-module projects to build successfully. To avoid failing the build in a module where no tests are present, add:
72+
[source,xml, role="multi-language-sample"]
73+
----
74+
<failNoTests>false</failNoTests>
75+
----
6476
`<debug>`::
6577
If you want to enable generation of debugging information, add:
6678
[source,xml, role="multi-language-sample"]
@@ -686,6 +698,76 @@ For example, you might wish to disable only native testing support for use cases
686698
- Your library or application uses a testing framework that is not supported on the JUnit Platform.
687699
- You need to use the <<agent-support, agent>> when running tests on the JVM but do not wish to run those same tests as native code.
688700

701+
[[control-test-execution]]
702+
=== Controlling test execution
703+
704+
==== Build, but not execute native tests
705+
706+
During a transition phase, it is often useful to build tests but not execute them. This allows inspection of the generated test image without failing the build when the tests do not execute successfully.
707+
708+
If you wish to build, but not execute, the native tests, invoke Maven with the `-DskipTestExecution` flag. This flag is specific to Native Build Tools.
709+
710+
[source,bash, role="multi-language-sample"]
711+
----
712+
./mvnw -Pnative -DskipTestExecution package
713+
----
714+
715+
Alternatively, set `<skipTestExecution>` to `true` in the plugin configuration:
716+
717+
[source,xml, role="multi-language-sample"]
718+
----
719+
<configuration>
720+
<skipTestExecution>true</skipTestExecution>
721+
</configuration>
722+
----
723+
724+
This will still build the native test image but skips execution of tests as native code.
725+
726+
==== Skip modules without native tests in multi-module builds
727+
728+
In multi-module projects where only some sub-modules contain native tests, you need to skip test execution for any module that does not contain native tests. Any module which should contain tests, but does not, should fail the build.
729+
730+
Skip test execution for modules by configuring the `<failNoTests>` configuration option for the full build and then overriding it in modules where the default behavior is not desired.
731+
732+
If the majority of the sub-modules should contain native tests, nothing needs to be configured globally since this is the default behavior for the native plugin.
733+
734+
For sub-modules that do not contain native tests but should not fail the build, add this to the module's _pom.xml_ in the module in the `<plugins>` section:
735+
736+
[source,xml, role="multi-language-sample"]
737+
----
738+
<plugin>
739+
<groupId>org.graalvm.buildtools</groupId>
740+
<artifactId>native-maven-plugin</artifactId>
741+
<configuration>
742+
<failNoTests>false</failNoTests>
743+
</configuration>
744+
</plugin>
745+
----
746+
747+
If only a few sub-modules contain native tests, add this configuration setting to the main plugin configuration:
748+
749+
[source,xml, role="multi-language-sample"]
750+
----
751+
<configuration>
752+
<failNoTests>false</failNoTests>
753+
</configuration>
754+
----
755+
756+
and then override this in any sub-module that should have native tests by adding this to the module in the `<plugins>` section:
757+
758+
[source,xml, role="multi-language-sample"]
759+
----
760+
<plugin>
761+
<groupId>org.graalvm.buildtools</groupId>
762+
<artifactId>native-maven-plugin</artifactId>
763+
<configuration>
764+
<failNoTests>true</failNoTests>
765+
</configuration>
766+
</plugin>
767+
----
768+
769+
For testing from the command line, the `-DfailNoTests=false` flag is also supported directly:
770+
689771
[[metadata-support]]
690772
== GraalVM Reachability Metadata Support
691773

Lines changed: 83 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,83 @@
1+
/*
2+
* Copyright (c) 2025, 2025, Oracle and/or its affiliates. All rights reserved.
3+
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4+
*
5+
* The Universal Permissive License (UPL), Version 1.0
6+
*
7+
* Subject to the condition set forth below, permission is hereby granted to any
8+
* person obtaining a copy of this software, associated documentation and/or
9+
* data (collectively the "Software"), free of charge and under any and all
10+
* copyright rights in the Software, and any and all patent rights owned or
11+
* freely licensable by each licensor hereunder covering either (i) the
12+
* unmodified Software as contributed to or provided by such licensor, or (ii)
13+
* the Larger Works (as defined below), to deal in both
14+
*
15+
* (a) the Software, and
16+
*
17+
* (b) any piece of software and/or hardware listed in the lrgrwrks.txt file if
18+
* one is included with the Software each a "Larger Work" to which the Software
19+
* is contributed by such licensors),
20+
*
21+
* without restriction, including without limitation the rights to copy, create
22+
* derivative works of, display, perform, and distribute the Software and make,
23+
* use, sell, offer for sale, import, export, have made, and have sold the
24+
* Software and the Larger Work(s), and to sublicense the foregoing rights on
25+
* either these or other terms.
26+
*
27+
* This license is subject to the following condition:
28+
*
29+
* The above copyright notice and either this complete permission notice or at a
30+
* minimum a reference to the UPL must be included in all copies or substantial
31+
* portions of the Software.
32+
*
33+
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
34+
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
35+
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
36+
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
37+
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
38+
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
39+
* SOFTWARE.
40+
*/
41+
42+
package org.graalvm.buildtools.maven
43+
44+
class MavenTestExecutionFunctionalTests extends AbstractGraalVMMavenFunctionalTest {
45+
def "test if the skipTestExecution flag skips execution of tests"() {
46+
withSample("java-application-with-tests")
47+
48+
when:
49+
mvn '-DquickBuild', '-DskipTestExecution=true', '-Pnative', 'test'
50+
51+
then:
52+
buildSucceeded
53+
outputContainsPattern ".*GraalVM Native Image: Generating 'native-tests.*?' \\(executable\\).*"
54+
outputDoesNotContain "containers found"
55+
outputDoesNotContain "containers skipped"
56+
outputDoesNotContain "containers started"
57+
outputDoesNotContain "tests found"
58+
outputDoesNotContain "tests skipped"
59+
outputDoesNotContain "tests started"
60+
}
61+
62+
def "test if clearing the failNoTests flag allows build to continue if no tests are present"() {
63+
withSample("non-native") // needs a sample that contains code in src/test but no actual test class
64+
65+
when:
66+
mvn '-DquickBuild', '-DfailNoTests=false', '-Pnative', 'test'
67+
68+
then:
69+
buildSucceeded
70+
outputContains "No tests found, skipping."
71+
}
72+
73+
def "test if setting the failNoTests flag fails the build if no tests are present"() {
74+
withSample("non-native") // needs a sample that contains code in src/test but no actual test class
75+
76+
when:
77+
mvn '-DquickBuild', '-DfailNoTests=true', '-Pnative', 'test'
78+
79+
then:
80+
buildFailed
81+
outputContains "Test configuration file wasn't found. Make sure that test execution wasn't skipped."
82+
}
83+
}

native-maven-plugin/src/main/java/org/graalvm/buildtools/maven/NativeTestMojo.java

Lines changed: 32 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -99,6 +99,27 @@ public class NativeTestMojo extends AbstractNativeImageMojo {
9999
@Parameter(property = "skipNativeTests", defaultValue = "false")
100100
private boolean skipNativeTests;
101101

102+
/**
103+
* Skips execution of native tests. If set to true, the plugin will create the native image for the tests but do not execute the tests.
104+
* This allows the creation of the native image for testing even if they don't fully execute / tests fail.
105+
* Otherwise, the build stops at the first test failure.
106+
*
107+
* @since 0.11.1
108+
*/
109+
@Parameter(property = "skipTestExecution", defaultValue = "false")
110+
private boolean skipTestExecution;
111+
112+
/**
113+
* Fail the build if no tests were found. In multi-module builds, there are often modules that have no tests (e.g. documentation)
114+
* or tests are enabled/disabled by profiles (slow tests, e2e tests etc.). This switch allows for a global configuration of the
115+
* native plugin and then skip any modules where no tests are present by changing this setting to false in the sub-module.
116+
* This allows such multi-module projects to build successfully.
117+
*
118+
* @since 0.11.1
119+
*/
120+
@Parameter(property = "failNoTests", defaultValue = "true")
121+
private boolean failNoTests;
122+
102123
@Override
103124
protected void populateApplicationClasspath() throws MojoExecutionException {
104125
super.populateApplicationClasspath();
@@ -151,8 +172,13 @@ public void execute() throws MojoExecutionException {
151172
return;
152173
}
153174
if (!hasTestIds()) {
154-
logger.error("Test configuration file wasn't found. Make sure that test execution wasn't skipped.");
155-
throw new IllegalStateException("Test configuration file wasn't found.");
175+
if (failNoTests) {
176+
logger.error("Test configuration file wasn't found. Make sure that test execution wasn't skipped.");
177+
throw new IllegalStateException("Test configuration file wasn't found.");
178+
} else {
179+
logger.info("No tests found, skipping.");
180+
return;
181+
}
156182
}
157183

158184
logger.info("====================");
@@ -178,7 +204,10 @@ public void execute() throws MojoExecutionException {
178204
mainClass = "org.graalvm.junit.platform.NativeImageJUnitLauncher";
179205

180206
buildImage();
181-
runNativeTests(outputDirectory.toPath().resolve(NATIVE_TESTS_EXE));
207+
208+
if (!skipTestExecution) {
209+
runNativeTests(outputDirectory.toPath().resolve(NATIVE_TESTS_EXE));
210+
}
182211
}
183212

184213
private void configureEnvironment() {

0 commit comments

Comments
 (0)