From c4b1c6006714e6c9c9a1182de2ceb45fcef808fe Mon Sep 17 00:00:00 2001 From: Matthew Gharrity Date: Fri, 10 Mar 2023 17:17:47 +0100 Subject: [PATCH] IDEA-314175 PathClassLoader disallows relative jar paths on the Java classpath GitOrigin-RevId: 0de0f55b91c8b7bfee04113c62a5441a14bda9bf --- .../src/com/intellij/util/lang/ClassPath.java | 5 ++++- .../com/intellij/util/lang/PathClassLoaderTest.kt | 15 +++++++++++++++ 2 files changed, 19 insertions(+), 1 deletion(-) diff --git a/platform/util-class-loader/src/com/intellij/util/lang/ClassPath.java b/platform/util-class-loader/src/com/intellij/util/lang/ClassPath.java index 67cee53c44ba..37fbd9d70631 100644 --- a/platform/util-class-loader/src/com/intellij/util/lang/ClassPath.java +++ b/platform/util-class-loader/src/com/intellij/util/lang/ClassPath.java @@ -339,7 +339,10 @@ public final class ClassPath { return null; } - Path path = files[searchOffset++]; + // https://youtrack.jetbrains.com/issue/IDEA-314175 + // some environments (e.g. Bazel tests) put relative jar paths on the Java classpath, + // because relative paths are useful for hermeticity. + Path path = files[searchOffset++].toAbsolutePath(); try { Loader loader = createLoader(path); if (loader != null) { diff --git a/platform/util/testSrc/com/intellij/util/lang/PathClassLoaderTest.kt b/platform/util/testSrc/com/intellij/util/lang/PathClassLoaderTest.kt index d66cbc2b5300..833d8d174f32 100644 --- a/platform/util/testSrc/com/intellij/util/lang/PathClassLoaderTest.kt +++ b/platform/util/testSrc/com/intellij/util/lang/PathClassLoaderTest.kt @@ -9,6 +9,8 @@ import org.junit.jupiter.api.Test import org.junit.jupiter.api.io.TempDir import java.net.URL import java.nio.file.Path +import java.nio.file.Paths +import kotlin.io.path.invariantSeparatorsPathString class PathClassLoaderTest { @Test @@ -24,4 +26,17 @@ class PathClassLoaderTest { assertThat(resource).isNotNull() assertThat(URL(resource!!.url, "screenshot.png").content).isEqualTo(expectedData) } + + @Test + fun `relative jar path`(@TempDir dir: Path) { + // Regression test for IDEA-314175. + val jarAbsolutePath = dir.resolve("lib.jar") + Compressor.Zip(jarAbsolutePath.toFile()).use { compressor -> + compressor.addFile("resource.txt", "contents".encodeToByteArray()) + } + val jarRelativePath = Paths.get("").toAbsolutePath().relativize(jarAbsolutePath) + val classPath = ClassPath(listOf(jarRelativePath), UrlClassLoader.build(), PathClassLoader.RESOURCE_FILE_FACTORY, true) + val resource = checkNotNull(classPath.findResource("resource.txt")) + assertThat(resource.url.toString()).isEqualTo("jar:file:${jarAbsolutePath.invariantSeparatorsPathString}!/resource.txt") + } } \ No newline at end of file