diff --git a/spring-boot-project/spring-boot/src/main/java/org/springframework/boot/AotProcessor.java b/spring-boot-project/spring-boot/src/main/java/org/springframework/boot/AotProcessor.java index 1a015f2a233..a2969e295ba 100644 --- a/spring-boot-project/spring-boot/src/main/java/org/springframework/boot/AotProcessor.java +++ b/spring-boot-project/spring-boot/src/main/java/org/springframework/boot/AotProcessor.java @@ -57,18 +57,29 @@ public class AotProcessor { private final Path resourceOutput; + private final String groupId; + + private final String artifactId; + /** * Create a new processor for the specified application and settings. * @param application the application main class * @param applicationArgs the arguments to provide to the main method * @param sourceOutput the location of generated sources * @param resourceOutput the location of generated resources + * @param groupId the group ID of the application, used to locate + * native-image.properties + * @param artifactId the artifact ID of the application, used to locate + * native-image.properties */ - public AotProcessor(Class application, String[] applicationArgs, Path sourceOutput, Path resourceOutput) { + public AotProcessor(Class application, String[] applicationArgs, Path sourceOutput, Path resourceOutput, + String groupId, String artifactId) { this.application = application; this.applicationArgs = applicationArgs; this.sourceOutput = sourceOutput; this.resourceOutput = resourceOutput; + this.groupId = groupId; + this.artifactId = artifactId; } /** @@ -123,7 +134,8 @@ public class AotProcessor { } private void writeGeneratedResources(RuntimeHints hints) { - FileNativeConfigurationWriter writer = new FileNativeConfigurationWriter(this.resourceOutput); + FileNativeConfigurationWriter writer = new FileNativeConfigurationWriter(this.resourceOutput, this.groupId, + this.artifactId); writer.write(hints); } @@ -137,7 +149,8 @@ public class AotProcessor { StringBuilder sb = new StringBuilder(); sb.append("Args = "); sb.append(String.join(String.format(" \\%n"), args)); - Path file = this.resourceOutput.resolve("META-INF/native-image/native-image.properties"); + Path file = this.resourceOutput + .resolve("META-INF/native-image/" + this.groupId + "/" + this.artifactId + "/native-image.properties"); try { if (!Files.exists(file)) { Files.createDirectories(file.getParent()); @@ -151,17 +164,21 @@ public class AotProcessor { } public static void main(String[] args) throws Exception { - if (args.length < 3) { + int requiredArgs = 5; + if (args.length < requiredArgs) { throw new IllegalArgumentException("Usage: " + AotProcessor.class.getName() - + " "); + + " "); } String applicationName = args[0]; Path sourceOutput = Paths.get(args[1]); Path resourceOutput = Paths.get(args[2]); - String[] applicationArgs = (args.length > 3) ? Arrays.copyOfRange(args, 3, args.length) : new String[0]; - + String groupId = args[3]; + String artifactId = args[4]; + String[] applicationArgs = (args.length > requiredArgs) ? Arrays.copyOfRange(args, requiredArgs, args.length) + : new String[0]; Class application = Class.forName(applicationName); - AotProcessor aotProcess = new AotProcessor(application, applicationArgs, sourceOutput, resourceOutput); + AotProcessor aotProcess = new AotProcessor(application, applicationArgs, sourceOutput, resourceOutput, groupId, + artifactId); aotProcess.process(); } diff --git a/spring-boot-project/spring-boot/src/test/java/org/springframework/boot/AotProcessorTests.java b/spring-boot-project/spring-boot/src/test/java/org/springframework/boot/AotProcessorTests.java index 66361530433..c4d913098b9 100644 --- a/spring-boot-project/spring-boot/src/test/java/org/springframework/boot/AotProcessorTests.java +++ b/spring-boot-project/spring-boot/src/test/java/org/springframework/boot/AotProcessorTests.java @@ -32,6 +32,7 @@ import static org.assertj.core.api.Assertions.assertThatIllegalArgumentException * Tests for {@link AotProcessor}. * * @author Stephane Nicoll + * @author Andy Wilkinson */ class AotProcessorTests { @@ -44,7 +45,7 @@ class AotProcessorTests { void processApplicationInvokesRunMethod(@TempDir Path directory) { String[] arguments = new String[] { "1", "2" }; AotProcessor processor = new AotProcessor(SampleApplication.class, arguments, directory.resolve("source"), - directory.resolve("resource")); + directory.resolve("resource"), "com.example", "example"); processor.process(); assertThat(SampleApplication.argsHolder).isEqualTo(arguments); assertThat(directory).satisfies(hasGeneratedAssetsForSampleApplication()); @@ -53,7 +54,7 @@ class AotProcessorTests { @Test void processApplicationWithMainMethodThatDoesNotRun(@TempDir Path directory) { AotProcessor processor = new AotProcessor(BrokenApplication.class, new String[0], directory.resolve("source"), - directory.resolve("resource")); + directory.resolve("resource"), "com.example", "example"); assertThatIllegalArgumentException().isThrownBy(processor::process) .withMessageContaining("Does it run a SpringApplication?"); assertThat(directory).isEmptyDirectory(); @@ -62,7 +63,8 @@ class AotProcessorTests { @Test void invokeMainParseArgumentsAndInvokesRunMethod(@TempDir Path directory) throws Exception { String[] mainArguments = new String[] { SampleApplication.class.getName(), - directory.resolve("source").toString(), directory.resolve("resource").toString(), "1", "2" }; + directory.resolve("source").toString(), directory.resolve("resource").toString(), "com.example", + "example", "1", "2" }; AotProcessor.main(mainArguments); assertThat(SampleApplication.argsHolder).containsExactly("1", "2"); assertThat(directory).satisfies(hasGeneratedAssetsForSampleApplication()); @@ -79,10 +81,10 @@ class AotProcessorTests { assertThat(directory .resolve("source/org/springframework/boot/SampleApplication__ApplicationContextInitializer.java")) .exists().isRegularFile(); - assertThat(directory.resolve("resource/META-INF/native-image/reflect-config.json")).exists() - .isRegularFile(); + assertThat(directory.resolve("resource/META-INF/native-image/com.example/example/reflect-config.json")) + .exists().isRegularFile(); Path nativeImagePropertiesFile = directory - .resolve("resource/META-INF/native-image/native-image.properties"); + .resolve("resource/META-INF/native-image/com.example/example/native-image.properties"); assertThat(nativeImagePropertiesFile).exists().isRegularFile().hasContent(""" Args = -H:Class=org.springframework.boot.AotProcessorTests$SampleApplication \\ --allow-incomplete-classpath \\