diff --git a/spring-native-docs/src/main/asciidoc/build-setup.adoc b/spring-native-docs/src/main/asciidoc/aot.adoc similarity index 68% rename from spring-native-docs/src/main/asciidoc/build-setup.adoc rename to spring-native-docs/src/main/asciidoc/aot.adoc index 1b79f3ff3..12d4742b4 100644 --- a/spring-native-docs/src/main/asciidoc/build-setup.adoc +++ b/spring-native-docs/src/main/asciidoc/aot.adoc @@ -1,10 +1,14 @@ -[[build-setup]] -== Build Setup -This section covers how to configure your build for <> or <>. -You'll also learn more about <> +[[aot]] +== AOT generation -[[build-setup-maven]] -=== Maven +This section covers AOT (Ahead Of Time) generation plugins, including how to configure your build for <> or <>. +You'll also learn more about <> and more details on the <>. + +[[aot-build-setup]] +=== Build setup + +[[aot-build-setup-maven]] +==== Maven The plugin should be declared in your `pom.xml` file: @@ -57,12 +61,12 @@ Configuration can be performed if needed within the `` element, f ---- -See <> for a list of the configuration options available. +See <> for a list of the configuration options available. -[[build-setup-gradle]] -=== Gradle +[[aot-build-setup-gradle]] +==== Gradle You can configure the Gradle Spring AOT plugin by declaring first the plugin repositories in your `settings.gradle(.kts)` file: @@ -168,12 +172,12 @@ springAot { NOTE: The non-idomatic `property.set(...)` syntax in the Gradle Kotlin DSL is due to https://github.com/gradle/gradle/issues/9268[gradle#9268], feel free to vote for this issue. -See <> for more details on the configuration options. +See <> for more details on the configuration options. -[[build-setup-configuration]] -=== AOT Configuration +[[aot-build-setup-configuration]] +==== AOT configuration The Spring AOT plugins allow you to express opinions about the source generation process. Here are all the options available: @@ -198,7 +202,7 @@ Here are all the options available: * `applicationClass` allows to specify an application class (typically annotated with `@SpringBootApplication`), useful when multiple ones are present. -==== Debugging the source generation +=== Debugging the source generation The Spring AOT plugins spawns a new process to perform the source generation. To remote debug this process, you can set a debug System property on the command line; then, the source generation process launches with a listener accepting a remote debugger on port `8000` for Maven or `5005` for Gradle. @@ -237,8 +241,8 @@ $ ./gradlew generateAot -Dorg.gradle.debug=true --no-daemon ---- -[[build-setup-modes]] -=== AOT Modes +[[aot-modes]] +=== AOT runtime modes The generated sources are automatically used by the native image compilation, but are not used by default when running your application with a JVM. This means that running the application or its tests from the IDE or the command line will not involve those classes. @@ -293,3 +297,58 @@ tasks.getByName("bootRun") { systemProperty("springAot", "true") } ---- + + +[[aot-engine]] +=== AOT engine + +Spring AOT inspects an application at build-time and generates an optimized version of it. +Based on your `@SpringBootApplication`-annotated main class, the AOT engine generates a persistent view of the beans that are going to be contributed at runtime in a way that bean instantiation is as straightforward as possible. +Additional post-processing of the factory is possible using callbacks. +For instance, these are used to generate the necessary <> that GraalVM needs to initialize the context in a native image. + +The engine goes through the following phases: + +. Prepare the underlying `BeanFactory` so that the relevant bean definitions are available. +This typically includes bean definitions model parsing (such as `@Configuration`-annotated classes) as well as any additional post-processing of the bean factory. +. Code generation based on the prepared `BeanFactory`. +Each bean definition is handled one by one and the necessary code to instantiate the bean and its necessary runtime semantics (such as primary flag) is generated. +. Additional processing of the bean factory used to optimize the runtime. + +[[aot-bean-factory-preparation]] +==== BeanFactory Preparation +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. + +While certain properties like passwords or url can be changed once the application has been prepared, properties that affect, typically, auto-configurations should be set at build-time. + +[NOTE] +==== +Conditions on the runtime environment, such as enabling features based on your chosen cloud platform, will no longer run at runtime. +==== + +A profile is a special sort of condition so these are also evaluated at build-time. +It is recommended to avoid the use of profiles as processing them at build-time does not allow you to enable or disable them at runtime anyway. +If you want to keep using them, they should be enabled at build-time, for instance by adding the `spring.profiles.active` property in `application.properties`. + +Low-level framework callbacks, such as `BeanDefinitionRegistryPostProcessor` are invoked at build-time to create any additional bean definitions. +To prevent such a callback to be invoked at runtime again, it is not registered as bean, unless it does not have an `infrastructure` role. + +[[aot-code-generation]] +==== Code Generation +Based on a bean name and a merged `RootBeanDefinition`, the engine identifies a suitable `BeanRegistrationWriter` that is responsible to write the necessary code to instantiate the bean at runtime. + +It is not expected that projects have to define their own writers, but this could happen for corner-cases. +Writers are identified via implementations of `BeanRegistrationWriterSupplier`, registered in `META-INF/spring.factories`. +Suppliers are ordered with a first-win approach, and a {github-tree}/spring-aot/src/main/java/org/springframework/aot/context/bootstrap/generator/bean/DefaultBeanRegistrationWriterSupplier.java[default implementation] with lowest precedence that handles most use cases is provided. + +NOTE: Explicit care is required if a bean requires privileged access in more than one package. +This happens typically if the bean use `protected` access and extends from another class in a different package that does the same. +As a rule of thumb, make sure that each custom bean of yours can be instantiated in a test in a usable form. + +[[aot-additional-processing]] +==== Additional Processing +Additional processing of the `BeanFactory` currently only scans for `@EventListener`-annotated methods, but future versions may provide additional implementations. + +More core to GraalVM support is the generation of an optimized set of native configuration based on the actual beans of the application, as covered by the next section. diff --git a/spring-native-docs/src/main/asciidoc/executable-jar-to-native.adoc b/spring-native-docs/src/main/asciidoc/executable-jar-to-native.adoc index 570e551f3..26b016e43 100644 --- a/spring-native-docs/src/main/asciidoc/executable-jar-to-native.adoc +++ b/spring-native-docs/src/main/asciidoc/executable-jar-to-native.adoc @@ -7,12 +7,12 @@ This can be useful for various use cases: * Keep the regular JVM pipeline and turn the JVM Spring Boot application to native on the CI/CD platform. * Keep an architecture neutral deployment artifact, as `native-image` https://github.com/oracle/graal/issues/407[does not support cross-compilation]. -WARNING: A mandatory pre-requisite is to use <> Maven or Gradle upstream to build the Spring Boot executable JAR. +WARNING: A mandatory pre-requisite is to use <> Maven or Gradle upstream to build the Spring Boot executable JAR. === With Buildpacks Spring Boot applications usually use {buildpacks}[Buildpacks] via the Maven (`mvn spring-boot:build-image`), or Gradle (`gradle bootBuildImage`) integration. -You can also use directly {buildpacks-docs}/tools/pack/[the `pack` CLI] to turn a Spring Boot executable JAR built with <> into an optimized container image. +You can also use directly {buildpacks-docs}/tools/pack/[the `pack` CLI] to turn a Spring Boot executable JAR built with <> into an optimized container image. First, make sure that a Docker daemon is available, either https://hub.docker.com/search?type=edition&offering=community[locally] or {buildpacks-docs}/app-developer-guide/build-a-windows-app/#using-remote-docker-hosts[remotely]. You also need to {buildpacks-docs}/tools/pack/[Install `pack`]. @@ -29,7 +29,7 @@ NOTE: This does not require a local `native-image` installation. === With `native-image` -Another option is to turn a Spring Boot executable JAR built with <> into a native executable using the GraalVM `native-image` compiler. +Another option is to turn a Spring Boot executable JAR built with <> into a native executable using the GraalVM `native-image` compiler. For this to work, you need to <>. Assuming a Spring Boot executable JAR built as `my-app-0.0.1-SNAPSHOT.jar` in the `target` directory: diff --git a/spring-native-docs/src/main/asciidoc/how-to-contribute.adoc b/spring-native-docs/src/main/asciidoc/how-to-contribute.adoc index a46abc3e8..7c7c43369 100644 --- a/spring-native-docs/src/main/asciidoc/how-to-contribute.adoc +++ b/spring-native-docs/src/main/asciidoc/how-to-contribute.adoc @@ -59,7 +59,7 @@ It is fine to use reflection in a native world but it is most optimal to do it i * In the static block/fields of a class initialized at build-time. * In an AOT transformation run as a Spring AOT build plugin. -NOTE: More guidelines will be provided here as <> matures. +NOTE: More guidelines will be provided here as <> matures. [[how-to-contribute-new-hints]] === Contributing new hints diff --git a/spring-native-docs/src/main/asciidoc/index.adoc b/spring-native-docs/src/main/asciidoc/index.adoc index a1474d5cd..7271ab0f9 100644 --- a/spring-native-docs/src/main/asciidoc/index.adoc +++ b/spring-native-docs/src/main/asciidoc/index.adoc @@ -41,21 +41,19 @@ Spring Native is composed of the following modules: * `spring-native-configuration`: configuration hints for Spring classes used by Spring AOT plugins, including various Spring Boot auto-configurations. * `spring-native-docs`: reference guide, in asciidoc format. * `spring-native-tools`: tools used for reviewing image building configuration and output. -* `spring-aot`: AOT transformation infrastructure common to Maven and Gradle plugins. -* `spring-aot-test`: Test-specific AOT transformation infrastructure. -* `spring-aot-gradle-plugin`: Gradle plugin that invokes AOT transformations. -* `spring-aot-maven-plugin`: Maven plugin that invokes AOT transformations. +* `spring-aot`: AOT generation infrastructure common to Maven and Gradle plugins. +* `spring-aot-test`: Test-specific AOT generation infrastructure. +* `spring-aot-gradle-plugin`: Gradle plugin that invokes AOT generation. +* `spring-aot-maven-plugin`: Maven plugin that invokes AOT generation. * `samples`: contains various samples that demonstrate features usage and are used as integration tests. [[getting-started]] -== Getting Started - -NOTE: Applications using Spring Native should be compiled with either Java 11 or Java 17. +== Getting started There are two main ways to build a Spring Boot native application: * Using <> to generate a lightweight container containing a native executable. -* Using <> to generate a native executable. +* Using <> to generate a native executable. TIP: The easiest way to start a new native Spring Boot project is to go to https://start.spring.io, add the "Spring Native" dependency and generate the project. @@ -65,12 +63,10 @@ include::getting-started-native-build-tools.adoc[] include::support.adoc[] -include::spring-aot.adoc[] +include::aot.adoc[] include::native-hints.adoc[] -include::build-setup.adoc[] - include::samples.adoc[] include::native-image-options.adoc[] diff --git a/spring-native-docs/src/main/asciidoc/spring-aot.adoc b/spring-native-docs/src/main/asciidoc/spring-aot.adoc deleted file mode 100644 index e1effb880..000000000 --- a/spring-native-docs/src/main/asciidoc/spring-aot.adoc +++ /dev/null @@ -1,52 +0,0 @@ -[[spring-aot]] -== Spring AOT -Spring AOT (Ahead-of-Time) inspects an application at build-time and generates an optimized version of it. -Based on your `@SpringBootApplication`-annotated main class, the AOT engine generates a persistent view of the beans that are going to be contributed at runtime in a way that bean instantiation is as straightforward as possible. -Additional post-processing of the factory is possible using callbacks. -For instance, these are used to generate the necessary <> that GraalVM needs to initialize the context in a native image. - -The engine goes through the following phases: - -. Prepare the underlying `BeanFactory` so that the relevant bean definitions are available. -This typically includes bean definitions model parsing (such as `@Configuration`-annotated classes) as well as any additional post-processing of the bean factory. -. Code generation based on the prepared `BeanFactory`. -Each bean definition is handled one by one and the necessary code to instantiate the bean and its necessary runtime semantics (such as primary flag) is generated. -. Additional processing of the bean factory used to optimize the runtime. - -[[spring-aot-bean-factory-preparation]] -=== BeanFactory Preparation -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. - -While certain properties like passwords or url can be changed once the application has been prepared, properties that affect, typically, auto-configurations should be set at build-time. - -[NOTE] -==== -Conditions on the runtime environment, such as enabling features based on your chosen cloud platform, will no longer run at runtime. -==== - -A profile is a special sort of condition so these are also evaluated at build-time. -It is recommended to avoid the use of profiles as processing them at build-time does not allow you to enable or disable them at runtime anyway. -If you want to keep using them, they should be enabled at build-time, for instance by adding the `spring.profiles.active` property in `application.properties`. - -Low-level framework callbacks, such as `BeanDefinitionRegistryPostProcessor` are invoked at build-time to create any additional bean definitions. -To prevent such a callback to be invoked at runtime again, it is not registered as bean, unless it does not have an `infrastructure` role. - -[[spring-aot-code-generation]] -=== Code Generation -Based on a bean name and a merged `RootBeanDefinition`, the engine identifies a suitable `BeanRegistrationWriter` that is responsible to write the necessary code to instantiate the bean at runtime. - -It is not expected that projects have to define their own writers, but this could happen for corner-cases. -Writers are identified via implementations of `BeanRegistrationWriterSupplier`, registered in `META-INF/spring.factories`. -Suppliers are ordered with a first-win approach, and a {github-tree}/spring-aot/src/main/java/org/springframework/aot/context/bootstrap/generator/bean/DefaultBeanRegistrationWriterSupplier.java[default implementation] with lowest precedence that handles most use cases is provided. - -NOTE: Explicit care is required if a bean requires privileged access in more than one package. -This happens typically if the bean use `protected` access and extends from another class in a different package that does the same. -As a rule of thumb, make sure that each custom bean of yours can be instantiated in a test in a usable form. - -[[spring-aot-additional-processing]] -=== Additional Processing -Additional processing of the `BeanFactory` currently only scans for `@EventListener`-annotated methods, but future versions may provide additional implementations. - -More core to GraalVM support is the generation of an optimized set of native configuration based on the actual beans of the application, as covered by the next section. diff --git a/spring-native-docs/src/main/asciidoc/troubleshooting.adoc b/spring-native-docs/src/main/asciidoc/troubleshooting.adoc index 739831c60..54550bf1a 100644 --- a/spring-native-docs/src/main/asciidoc/troubleshooting.adoc +++ b/spring-native-docs/src/main/asciidoc/troubleshooting.adoc @@ -27,7 +27,7 @@ Error: Classes that should be initialized at run time got initialized during ima ---- You have probably tried to compile a Spring Boot application to native without the `spring-native` dependency and Spring AOT plugin. -See related <> and <> documentation. +See related <> and <> documentation. ==== WARNING: Could not register reflection metadata