This is an automated email from the ASF dual-hosted git repository. ppkarwasz pushed a commit to branch feat/2.x/uniform-uri-conversion in repository https://gitbox.apache.org/repos/asf/logging-log4j2.git
commit 7edba86f2669cc2e5bfc39ac972eafbc866ba2f6 Author: Piotr P. Karwasz <[email protected]> AuthorDate: Sat Jun 27 13:40:14 2026 +0200 Add cross-platform tests for `NetUtils.toURI` conversion Rework `NetUtilsTest` into parameterized cases that pin down how a string (a URI or a file system path) is converted to a `URI` on both UNIX and Windows. Every input is exercised on every OS; only the expected result differs, selected through `SystemUtils.IS_OS_WINDOWS`. These tests describe the intended, uniform behavior and therefore fail against the current `NetUtils.toURI` implementation. The fix follows in the next commit. Assisted-By: Claude Opus 4.8 <[email protected]> --- .../logging/log4j/core/util/NetUtilsTest.java | 118 +++++++++++++-------- 1 file changed, 76 insertions(+), 42 deletions(-) diff --git a/log4j-core-test/src/test/java/org/apache/logging/log4j/core/util/NetUtilsTest.java b/log4j-core-test/src/test/java/org/apache/logging/log4j/core/util/NetUtilsTest.java index 9afa5f2069..562140351d 100644 --- a/log4j-core-test/src/test/java/org/apache/logging/log4j/core/util/NetUtilsTest.java +++ b/log4j-core-test/src/test/java/org/apache/logging/log4j/core/util/NetUtilsTest.java @@ -18,67 +18,101 @@ package org.apache.logging.log4j.core.util; import static org.assertj.core.api.Assertions.assertThat; import static org.assertj.core.api.Assumptions.assumeThat; -import static org.junit.jupiter.api.Assertions.assertEquals; -import static org.junit.jupiter.api.Assertions.assertNotNull; +import static org.junit.jupiter.params.provider.Arguments.arguments; -import java.io.File; import java.net.InetAddress; import java.net.URI; import java.net.UnknownHostException; +import java.util.stream.Stream; +import org.apache.commons.lang3.SystemUtils; import org.junit.jupiter.api.Test; -import org.junit.jupiter.api.condition.EnabledOnOs; -import org.junit.jupiter.api.condition.OS; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.Arguments; +import org.junit.jupiter.params.provider.MethodSource; class NetUtilsTest { - @Test - void testToUriWithoutBackslashes() { - final String config = "file:///path/to/something/on/unix"; - URI uri = NetUtils.toURI(config); - - assertNotNull(uri, "The URI should not be null."); - assertEquals("file:///path/to/something/on/unix", uri.toString(), "The URI is not correct."); - - final String properUriPath = "/path/without/spaces"; - uri = NetUtils.toURI(properUriPath); - - assertNotNull(uri, "The URI should not be null."); - assertEquals(properUriPath, uri.toString(), "The URI is not correct."); + /** + * {@link NetUtils#toURI(String)} over a mix of URIs and file system paths. + * + * <p>Every input is exercised on every OS. Only the expected result differs.</p> + */ + @ParameterizedTest + @MethodSource + void toUriConvertsLocationsToUris(final String input, final String expected) { + assertThat(NetUtils.toURI(input)).hasToString(expected); } - @Test - void testToUriUnixWithSpaces() { - final String pathWithSpaces = "/ path / with / spaces"; - final URI uri = NetUtils.toURI(pathWithSpaces); - - assertNotNull(uri, "The URI should not be null."); - assertEquals(new File(pathWithSpaces).toURI().toString(), uri.toString(), "The URI is not correct."); + static Stream<Arguments> toUriConvertsLocationsToUris() { + return Stream.of( + // Genuine absolute URIs are returned verbatim on every platform. + arguments("file:///path/to/something/on/unix", "file:///path/to/something/on/unix"), + arguments("classpath:log4j2.xml", "classpath:log4j2.xml"), + arguments("classloader:log4j2.xml", "classloader:log4j2.xml"), + arguments("vfsfile:/some/path/log4j2.xml", "vfsfile:/some/path/log4j2.xml"), + // Well-formed layered Apache Commons VFS URLs are valid (opaque) URIs, returned verbatim. + arguments("zip:file:///path/a.zip!/dir/log4j2.xml", "zip:file:///path/a.zip!/dir/log4j2.xml"), + arguments( + "tar:gz:http://example.com/a.tar.gz!/a.tar!/log4j2.xml", + "tar:gz:http://example.com/a.tar.gz!/a.tar!/log4j2.xml"), + // Blanks are illegal in a URI: a hierarchical URL is rebuilt with them encoded, preserving user info, + // host, port and query. + arguments( + "http://example.com/a b/log4j2.xml?env=prod x", + "http://example.com/a%20b/log4j2.xml?env=prod%20x"), + arguments( + "https://[email protected]:8443/a b/log4j2.xml", + "https://[email protected]:8443/a%20b/log4j2.xml"), + // A relative path stays a scheme-less relative URI on every platform. + arguments("relative/path/log4j2.xml", "relative/path/log4j2.xml"), + // The remaining inputs are file system paths: absolute on one OS (resolved to a `file:` URI) and + // relative on the other (a scheme-less URI, any drive-letter colon escaped to `%3A`). + perOs("/path/without/spaces", "/path/without/spaces", "file:/path/without/spaces"), + perOs( + "/ path / with / spaces", + "/%20path%20/%20with%20/%20spaces", + "file:/%20path%20/%20with%20/%20spaces"), + perOs("C:/dir/log4j2.xml", "file:/C:/dir/log4j2.xml", "C%3A/dir/log4j2.xml"), + perOs("C:\\dir\\log4j2.xml", "file:/C:/dir/log4j2.xml", "C%3A%5Cdir%5Clog4j2.xml"), + perOs( + "D:\\path\\to\\something\\on\\windows", + "file:/D:/path/to/something/on/windows", + "D%3A%5Cpath%5Cto%5Csomething%5Con%5Cwindows"), + perOs( + "file:///D:\\path\\to\\something/on/windows", + "file:///D:/path/to/something/on/windows", + "file:///D:%5Cpath%5Cto%5Csomething/on/windows")); } - @Test - @EnabledOnOs(OS.WINDOWS) - void testToUriWindowsWithBackslashes() { - final String config = "file:///D:\\path\\to\\something/on/windows"; - final URI uri = NetUtils.toURI(config); - - assertNotNull(uri, "The URI should not be null."); - assertEquals("file:///D:/path/to/something/on/windows", uri.toString(), "The URI is not correct."); + /** + * Builds a case whose expected {@code toString()} differs between Windows and the other platforms. + */ + private static Arguments perOs(final String input, final String onWindows, final String onUnix) { + return arguments(input, SystemUtils.IS_OS_WINDOWS ? onWindows : onUnix); } - @Test - @EnabledOnOs(OS.WINDOWS) - void testToUriWindowsAbsolutePath() { - final String config = "D:\\path\\to\\something\\on\\windows"; - final URI uri = NetUtils.toURI(config); + @ParameterizedTest + @MethodSource + void toUrisSplitsOnComma(final String input, final String[] expected) { + assertThat(NetUtils.toURIs(input)).extracting(URI::toString).containsExactly(expected); + } - assertNotNull(uri, "The URI should not be null."); - assertEquals("file:/D:/path/to/something/on/windows", uri.toString(), "The URI is not correct."); + static Stream<Arguments> toUrisSplitsOnComma() { + return Stream.of( + // A single location yields a single URI. + arguments("classpath:log4j2.xml", new String[] {"classpath:log4j2.xml"}), + // The scheme of the first location is propagated to the following ones, and blanks around the comma are + // trimmed. + arguments("classpath:first.xml, second.xml", new String[] {"classpath:first.xml", "classpath:second.xml" + }), + // Without a scheme each (relative) location is kept as-is. + arguments("a/first.xml,b/second.xml", new String[] {"a/first.xml", "b/second.xml"})); } @Test - void testCanonicalHostName() throws UnknownHostException { + void canonicalHostNameContainsDot() throws UnknownHostException { assumeThat(InetAddress.getLocalHost().getCanonicalHostName()).contains("."); - // If this fails the host might be misconfigured + // If this fails the host might be misconfigured. assertThat(NetUtils.getCanonicalLocalHostname()).contains("."); } }
