diff --git a/spring-boot-project/spring-boot-tools/spring-boot-jarmode-layertools/build.gradle b/spring-boot-project/spring-boot-tools/spring-boot-jarmode-layertools/build.gradle index 79c8841f66..03bc7579bd 100644 --- a/spring-boot-project/spring-boot-tools/spring-boot-jarmode-layertools/build.gradle +++ b/spring-boot-project/spring-boot-tools/spring-boot-jarmode-layertools/build.gradle @@ -11,7 +11,6 @@ dependencies { api(platform(project(":spring-boot-project:spring-boot-parent"))) implementation(project(":spring-boot-project:spring-boot-tools:spring-boot-loader")) - implementation(project(":spring-boot-project:spring-boot")) implementation("org.springframework:spring-core") testImplementation("org.assertj:assertj-core") diff --git a/spring-boot-project/spring-boot-tools/spring-boot-jarmode-layertools/src/main/java/org/springframework/boot/jarmode/layertools/Context.java b/spring-boot-project/spring-boot-tools/spring-boot-jarmode-layertools/src/main/java/org/springframework/boot/jarmode/layertools/Context.java index d072d120aa..e4d40bff19 100644 --- a/spring-boot-project/spring-boot-tools/spring-boot-jarmode-layertools/src/main/java/org/springframework/boot/jarmode/layertools/Context.java +++ b/spring-boot-project/spring-boot-tools/spring-boot-jarmode-layertools/src/main/java/org/springframework/boot/jarmode/layertools/Context.java @@ -17,9 +17,16 @@ package org.springframework.boot.jarmode.layertools; import java.io.File; +import java.io.IOException; +import java.net.JarURLConnection; +import java.net.URISyntaxException; +import java.net.URL; +import java.net.URLConnection; import java.nio.file.Paths; +import java.security.CodeSource; +import java.security.ProtectionDomain; +import java.util.jar.JarFile; -import org.springframework.boot.system.ApplicationHome; import org.springframework.util.Assert; /** @@ -39,7 +46,7 @@ class Context { * Create a new {@link Context} instance. */ Context() { - this(new ApplicationHome().getSource(), Paths.get(".").toAbsolutePath().normalize().toFile()); + this(getSourceJarFile(), Paths.get(".").toAbsolutePath().normalize().toFile()); } /** @@ -55,6 +62,39 @@ class Context { this.relativeDir = deduceRelativeDir(jarFile.getParentFile(), this.workingDir); } + private static File getSourceJarFile() { + try { + ProtectionDomain domain = Context.class.getProtectionDomain(); + CodeSource codeSource = (domain != null) ? domain.getCodeSource() : null; + URL location = (codeSource != null) ? codeSource.getLocation() : null; + File source = (location != null) ? findSource(location) : null; + if (source != null && source.exists()) { + return source.getAbsoluteFile(); + } + return null; + } + catch (Exception ex) { + return null; + } + } + + private static File findSource(URL location) throws IOException, URISyntaxException { + URLConnection connection = location.openConnection(); + if (connection instanceof JarURLConnection) { + return getRootJarFile(((JarURLConnection) connection).getJarFile()); + } + return new File(location.toURI()); + } + + private static File getRootJarFile(JarFile jarFile) { + String name = jarFile.getName(); + int separator = name.indexOf("!/"); + if (separator > 0) { + name = name.substring(0, separator); + } + return new File(name); + } + private String deduceRelativeDir(File sourceFolder, File workingDir) { String sourcePath = sourceFolder.getAbsolutePath(); String workingPath = workingDir.getAbsolutePath();