Ahead-of-Time Processing
Spring AOT is a process that analyzes your application at build-time and generate an optimized version of it.
It is a mandatory step to run a Spring ApplicationContext
in a native image.
For an overview of GraalVM Native Images support in Spring Boot, check the reference documentation. |
The Spring Boot Maven plugin offers goals that can be used to perform AOT processing on both application and test code.
Processing Applications
To configure your application to use this feature, add an execution for the process-aot
goal, as shown in the following example:
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<executions>
<execution>
<id>process-aot</id>
<goals>
<goal>process-aot</goal>
</goals>
</execution>
</executions>
</plugin>
As the BeanFactory
is fully prepared at build-time, conditions are also evaluated.
This has an important difference compared to what a regular Spring Boot application does at runtime.
For instance, if you want to opt-in or opt-out for certain features, you need to configure the environment used at build time to do so.
The process-aot
goal shares a number of properties with the run goal for that reason.
Using the Native Profile
If you use spring-boot-starter-parent
as the parent
of your project, a native
profile can be used to streamline the steps required to build a native image.
The native
profile configures the following:
-
Execution of
process-aot
when the Spring Boot Maven Plugin is applied on a project. -
Suitable settings so that build-image generates a native image.
-
Sensible defaults for the Native Build Tools Maven Plugin, in particular:
-
Making sure the plugin uses the raw classpath, and not the main jar file as it does not understand our repackaged jar format.
-
Validate that a suitable GraalVM version is available.
-
Download third-party reachability metadata.
-
The use of the raw classpath means that native image does not know about the generated |
To benefit from the native
profile, a module that represents an application should define two plugins, as shown in the following example:
<plugin>
<groupId>org.graalvm.buildtools</groupId>
<artifactId>native-maven-plugin</artifactId>
</plugin>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
A single project can trigger the generation of a native image on the command-line using either Cloud Native Buildpacks or Native Image Build Tools.
To use the native
profile with a multi-modules project, you can create a customization of the native
profile so that it invokes your preferred technique.
To bind Cloud Native Buildpacks during the package
phase, add the following to the root POM of your multi-modules project:
<profile>
<id>native</id>
<build>
<pluginManagement>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<executions>
<execution>
<id>build-image</id>
<goals>
<goal>build-image-no-fork</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</pluginManagement>
</build>
</profile>
The example below does the same for Native Build Tools:
<profile>
<id>native</id>
<build>
<pluginManagement>
<plugins>
<plugin>
<groupId>org.graalvm.buildtools</groupId>
<artifactId>native-maven-plugin</artifactId>
<executions>
<execution>
<id>build-image</id>
<goals>
<goal>compile-no-fork</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</pluginManagement>
</build>
</profile>
Once the above is in place, you can build your multi-modules project and generate a native image in the relevant sub-modules, as shown in the following example:
$ mvn package -Pnative
A "relevant" sub-module is a module that represents a Spring Boot application. Such module must define the Native Build Tools and Spring Boot plugins as described above. |
spring-boot:process-aot
org.springframework.boot:spring-boot-maven-plugin:3.3.5
Invoke the AOT engine on the application.
Required parameters
Name | Type | Default |
---|---|---|
|
|
|
|
|
|
|
|
|
|
|
Optional parameters
Name | Type | Default |
---|---|---|
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
|
|
|
Parameter details
arguments
Application arguments that should be taken into account for AOT processing.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
classesDirectory
Directory containing the classes and resource files that should be packaged into the archive.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
compilerArguments
Arguments that should be provided to the AOT compile process. On command line, make sure to wrap multiple values between quotes.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
excludeGroupIds
Comma separated list of groupId names to exclude (exact match).
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
|
excludes
Collection of artifact definitions to exclude. The Exclude
element defines mandatory groupId
and artifactId
components and an optional classifier
component. When configured as a property, values should be comma-separated with colon-separated components: groupId:artifactId,groupId:artifactId:classifier
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
|
generatedClasses
Directory containing the generated classes.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
generatedResources
Directory containing the generated resources.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
generatedSources
Directory containing the generated sources.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
includes
Collection of artifact definitions to include. The Include
element defines mandatory groupId
and artifactId
components and an optional classifier
component. When configured as a property, values should be comma-separated with colon-separated components: groupId:artifactId,groupId:artifactId:classifier
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
|
jvmArguments
JVM arguments that should be associated with the AOT process. On command line, make sure to wrap multiple values between quotes.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
mainClass
Name of the main class to use as the source for the AOT process. If not specified the first compiled class found that contains a 'main' method will be used.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
profiles
Spring profiles to take into account for AOT processing.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
Processing Tests
The AOT engine can be applied to JUnit 5 tests that use Spring’s Test Context Framework.
Suitable tests are processed by the AOT engine in order to generate ApplicationContextInitializer
code.
To configure your application to use this feature, add an execution for the process-test-aot
goal, as shown in the following example:
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<executions>
<execution>
<id>process-test-aot</id>
<goals>
<goal>process-test-aot</goal>
</goals>
</execution>
</executions>
</plugin>
If you are using spring-boot-starter-parent , this execution is automatically configured if you enable the nativeTest profile.
|
As with application AOT processing, the BeanFactory
is fully prepared at build-time.
spring-boot:process-test-aot
org.springframework.boot:spring-boot-maven-plugin:3.3.5
Invoke the AOT engine on tests.
Required parameters
Name | Type | Default |
---|---|---|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
Parameter details
classesDirectory
Directory containing the classes and resource files that should be used to run the tests.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
compilerArguments
Arguments that should be provided to the AOT compile process. On command line, make sure to wrap multiple values between quotes.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
excludeGroupIds
Comma separated list of groupId names to exclude (exact match).
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
|
excludes
Collection of artifact definitions to exclude. The Exclude
element defines mandatory groupId
and artifactId
components and an optional classifier
component. When configured as a property, values should be comma-separated with colon-separated components: groupId:artifactId,groupId:artifactId:classifier
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
|
generatedClasses
Directory containing the generated test classes.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
generatedResources
Directory containing the generated test resources.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
generatedSources
Directory containing the generated sources.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
generatedTestClasses
Directory containing the generated test classes.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
includes
Collection of artifact definitions to include. The Include
element defines mandatory groupId
and artifactId
components and an optional classifier
component. When configured as a property, values should be comma-separated with colon-separated components: groupId:artifactId,groupId:artifactId:classifier
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
|
jvmArguments
JVM arguments that should be associated with the AOT process. On command line, make sure to wrap multiple values between quotes.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |
skip
Skip the execution.
Name |
|
---|---|
Type |
|
Default value |
|
User property |
|
Since |