diff --git a/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/URIUtil.java b/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/URIUtil.java
index f663a228569..8825d08dab0 100644
--- a/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/URIUtil.java
+++ b/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/URIUtil.java
@@ -16,10 +16,12 @@ package org.eclipse.jetty.util;
import java.io.File;
import java.io.IOException;
import java.net.URI;
+import java.net.URISyntaxException;
import java.net.URL;
import java.net.URLClassLoader;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
+import java.nio.file.InvalidPathException;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.ArrayList;
@@ -1640,7 +1642,7 @@ public final class URIUtil
// Correct any bad `file:/path` usages, and
// force encoding of characters that must be encoded (such as unicode)
// for the base
- String base = correctFileURI(uri).toASCIIString();
+ String base = correctURI(uri).toASCIIString();
// ensure that the base has a safe encoding suitable for both
// URI and Paths.get(URI) later usage
@@ -1698,8 +1700,36 @@ public final class URIUtil
*
* @param uri the URI to (possibly) correct
* @return the new URI with the {@code file:/} substring corrected, or the original URI.
+ * @deprecated use {@link #correctURI(URI)} instead, will be removed in Jetty 12.1.0
*/
+ @Deprecated(since = "12.0.7", forRemoval = true)
public static URI correctFileURI(URI uri)
+ {
+ return correctURI(uri);
+ }
+
+ /**
+ *
+ * Corrects any bad {@code file} based URIs (even within a {@code jar:file:} based URIs) from the bad out-of-spec
+ * format that various older Java APIs creates (most notably: {@link java.io.File} creates with it's {@link File#toURL()}
+ * and {@link File#toURI()}, along with the side effects of using {@link URL#toURI()})
+ *
+ *
+ *
+ * This correction is currently limited to only the {@code file:/} substring in the URI.
+ * If there is a {@code file:/} detected, that substring is corrected to
+ * {@code file:///}, all other uses of {@code file:}, and URIs without a {@code file:}
+ * substring are left alone.
+ *
+ *
+ *
+ * Note that Windows UNC based URIs are left alone, along with non-absolute URIs.
+ *
+ *
+ * @param uri the URI to (possibly) correct
+ * @return the new URI with the {@code file:} scheme specific part corrected, or the original URI.
+ */
+ public static URI correctURI(URI uri)
{
if ((uri == null) || (uri.getScheme() == null))
return uri;
@@ -1845,10 +1875,60 @@ public final class URIUtil
{
Objects.requireNonNull(resource);
- // Only try URI for string for known schemes, otherwise assume it is a Path
- return (ResourceFactory.isSupported(resource))
- ? correctFileURI(URI.create(resource))
- : Paths.get(resource).toUri();
+ if (URIUtil.hasScheme(resource))
+ {
+ try
+ {
+ URI uri = new URI(resource);
+
+ if (ResourceFactory.isSupported(uri))
+ return correctURI(uri);
+
+ // We don't have a supported URI scheme
+ if (uri.getScheme().length() == 1)
+ {
+ // Input is a possible Windows path disguised as a URI "D:/path/to/resource.txt".
+ try
+ {
+ return toURI(Paths.get(resource).toUri().toASCIIString());
+ }
+ catch (InvalidPathException x)
+ {
+ LOG.trace("ignored", x);
+ }
+ }
+
+ // If we reached this point, that means the input String has a scheme,
+ // and is not recognized as supported by the registered schemes in ResourceFactory.
+ if (LOG.isDebugEnabled())
+ LOG.debug("URI scheme is not registered: {}", uri.toASCIIString());
+ throw new IllegalArgumentException("URI scheme not registered: " + uri.getScheme());
+ }
+ catch (URISyntaxException x)
+ {
+ // We have an input string that has what looks like a scheme, but isn't a URI.
+ // Eg: "C:\path\to\resource.txt"
+ LOG.trace("ignored", x);
+ }
+ }
+
+ // If we reached this point, we have a String with no valid scheme.
+ // Treat it as a Path, as that's all we have left to investigate.
+ try
+ {
+ return toURI(Paths.get(resource).toUri().toASCIIString());
+ }
+ catch (InvalidPathException x)
+ {
+ LOG.trace("ignored", x);
+ }
+
+ // If we reached this here, that means the input string cannot be used as
+ // a URI or a File Path. The cause is usually due to bad input (eg:
+ // characters that are not supported by file system)
+ if (LOG.isDebugEnabled())
+ LOG.debug("Input string cannot be converted to URI \"{}\"", resource);
+ throw new IllegalArgumentException("Cannot be converted to URI");
}
/**
@@ -1929,7 +2009,7 @@ public final class URIUtil
.map(URL::toString)
.map(URI::create)
.map(URIUtil::unwrapContainer)
- .map(URIUtil::correctFileURI);
+ .map(URIUtil::correctURI);
}
private static final Index DEFAULT_PORT_FOR_SCHEME = new Index.Builder()
diff --git a/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/PathResource.java b/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/PathResource.java
index 6c68b6728de..14013f9d557 100644
--- a/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/PathResource.java
+++ b/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/PathResource.java
@@ -171,7 +171,7 @@ public class PathResource extends Resource
{
String uriString = uri.toASCIIString();
if (!uriString.endsWith("/"))
- uri = URIUtil.correctFileURI(URI.create(uriString + "/"));
+ uri = URIUtil.correctURI(URI.create(uriString + "/"));
}
this.path = path;
diff --git a/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/Resource.java b/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/Resource.java
index cae05a53dfd..37c417a001e 100644
--- a/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/Resource.java
+++ b/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/Resource.java
@@ -109,8 +109,8 @@ public abstract class Resource implements Iterable
return false;
// Ensure that if `file` scheme is used, it's using a consistent convention to allow for startsWith check
- String thisURIString = URIUtil.correctFileURI(thisURI).toASCIIString();
- String otherURIString = URIUtil.correctFileURI(otherURI).toASCIIString();
+ String thisURIString = URIUtil.correctURI(thisURI).toASCIIString();
+ String otherURIString = URIUtil.correctURI(otherURI).toASCIIString();
return otherURIString.startsWith(thisURIString) &&
(thisURIString.length() == otherURIString.length() || otherURIString.charAt(thisURIString.length()) == '/');
@@ -315,7 +315,7 @@ public abstract class Resource implements Iterable
}
return;
}
- throw new UnsupportedOperationException("Directory Resources without a Path must implement copyTo");
+ throw new UnsupportedOperationException("Directory Resources without a Path must implement copyTo: " + this);
}
// Do we have to copy a single file?
@@ -326,12 +326,18 @@ public abstract class Resource implements Iterable
{
// to a directory, preserve the filename
Path destPath = destination.resolve(src.getFileName().toString());
- Files.copy(src, destPath, StandardCopyOption.COPY_ATTRIBUTES, StandardCopyOption.REPLACE_EXISTING);
+ Files.copy(src, destPath,
+ StandardCopyOption.ATOMIC_MOVE,
+ StandardCopyOption.COPY_ATTRIBUTES,
+ StandardCopyOption.REPLACE_EXISTING);
}
else
{
// to a file, use destination as-is
- Files.copy(src, destination, StandardCopyOption.COPY_ATTRIBUTES, StandardCopyOption.REPLACE_EXISTING);
+ Files.copy(src, destination,
+ StandardCopyOption.ATOMIC_MOVE,
+ StandardCopyOption.COPY_ATTRIBUTES,
+ StandardCopyOption.REPLACE_EXISTING);
}
return;
}
diff --git a/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/ResourceFactoryInternals.java b/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/ResourceFactoryInternals.java
index a870ae70596..847659a0890 100644
--- a/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/ResourceFactoryInternals.java
+++ b/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/ResourceFactoryInternals.java
@@ -213,13 +213,13 @@ class ResourceFactoryInternals
// otherwise resolve against the current directory
uri = CURRENT_WORKING_DIR.toUri().resolve(uri);
- // Correct any `file:/path` to `file:///path` mistakes
- uri = URIUtil.correctFileURI(uri);
+ // Correct any mistakes like `file:/path` (to `file:///path`)
+ uri = URIUtil.correctURI(uri);
}
ResourceFactory resourceFactory = RESOURCE_FACTORIES.get(uri.getScheme());
if (resourceFactory == null)
- throw new IllegalArgumentException("URI scheme not supported: " + uri);
+ throw new IllegalArgumentException("URI scheme not registered: " + uri.getScheme());
if (resourceFactory instanceof MountedPathResourceFactory)
{
FileSystemPool.Mount mount = mountIfNeeded(uri);
@@ -233,7 +233,9 @@ class ResourceFactoryInternals
}
catch (URISyntaxException | ProviderNotFoundException ex)
{
- throw new IllegalArgumentException("Unable to create resource from: " + uri, ex);
+ if (LOG.isDebugEnabled())
+ LOG.debug("Unable to create resource from: {}", uri, ex);
+ throw new IllegalArgumentException("Unable to create resource", ex);
}
}
diff --git a/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/URLResourceFactory.java b/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/URLResourceFactory.java
index cbff9509b49..f186bb23c72 100644
--- a/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/URLResourceFactory.java
+++ b/jetty-core/jetty-util/src/main/java/org/eclipse/jetty/util/resource/URLResourceFactory.java
@@ -176,7 +176,7 @@ public class URLResourceFactory implements ResourceFactory
@Override
public URI getURI()
{
- return URIUtil.correctFileURI(uri);
+ return URIUtil.correctURI(uri);
}
@Override
diff --git a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/URIUtilTest.java b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/URIUtilTest.java
index 16a6e55e448..e482337f0b0 100644
--- a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/URIUtilTest.java
+++ b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/URIUtilTest.java
@@ -57,7 +57,6 @@ import static org.junit.jupiter.api.Assumptions.assumeTrue;
@ExtendWith(WorkDirExtension.class)
public class URIUtilTest
{
-
public WorkDir workDir;
public static Stream encodePathSource()
@@ -668,10 +667,10 @@ public class URIUtilTest
@ParameterizedTest
@MethodSource("correctBadFileURICases")
- public void testCorrectFileURI(String input, String expected)
+ public void testCorrectURI(String input, String expected)
{
URI inputUri = URI.create(input);
- URI actualUri = URIUtil.correctFileURI(inputUri);
+ URI actualUri = URIUtil.correctURI(inputUri);
URI expectedUri = URI.create(expected);
assertThat(actualUri.toASCIIString(), is(expectedUri.toASCIIString()));
}
@@ -695,8 +694,8 @@ public class URIUtilTest
assertThat(fileUri.toASCIIString(), not(containsString("://")));
assertThat(fileUrlUri.toASCIIString(), not(containsString("://")));
- assertThat(URIUtil.correctFileURI(fileUri).toASCIIString(), is(expectedUri.toASCIIString()));
- assertThat(URIUtil.correctFileURI(fileUrlUri).toASCIIString(), is(expectedUri.toASCIIString()));
+ assertThat(URIUtil.correctURI(fileUri).toASCIIString(), is(expectedUri.toASCIIString()));
+ assertThat(URIUtil.correctURI(fileUrlUri).toASCIIString(), is(expectedUri.toASCIIString()));
}
public static Stream encodeSpecific()
@@ -1063,6 +1062,49 @@ public class URIUtilTest
assertThat(actual.toASCIIString(), is(expected));
}
+ public static Stream toURICases()
+ {
+ List args = new ArrayList<>();
+
+ if (OS.WINDOWS.isCurrentOs())
+ {
+ // Windows format (absolute and relative)
+ args.add(Arguments.of("C:\\path\\to\\foo.jar", "file:///C:/path/to/foo.jar"));
+ args.add(Arguments.of("D:\\path\\to\\bogus.txt", "file:///D:/path/to/bogus.txt"));
+ args.add(Arguments.of("\\path\\to\\foo.jar", "file:///C:/path/to/foo.jar"));
+ args.add(Arguments.of("\\path\\to\\bogus.txt", "file:///C:/path/to/bogus.txt"));
+ // unix format (relative)
+ args.add(Arguments.of("C:/path/to/foo.jar", "file:///C:/path/to/foo.jar"));
+ args.add(Arguments.of("D:/path/to/bogus.txt", "file:///D:/path/to/bogus.txt"));
+ args.add(Arguments.of("/path/to/foo.jar", "file:///C:/path/to/foo.jar"));
+ args.add(Arguments.of("/path/to/bogus.txt", "file:///C:/path/to/bogus.txt"));
+ // URI format (absolute)
+ args.add(Arguments.of("file:///D:/path/to/zed.jar", "file:///D:/path/to/zed.jar"));
+ args.add(Arguments.of("file:/e:/zed/yotta.txt", "file:///e:/zed/yotta.txt"));
+ args.add(Arguments.of("jar:file:///E:/path/to/bar.jar", "jar:file:///E:/path/to/bar.jar"));
+ }
+ else
+ {
+ // URI (and unix) format (relative)
+ args.add(Arguments.of("/path/to/foo.jar", "file:///path/to/foo.jar"));
+ args.add(Arguments.of("/path/to/bogus.txt", "file:///path/to/bogus.txt"));
+ }
+ // URI format (absolute)
+ args.add(Arguments.of("file:///path/to/zed.jar", "file:///path/to/zed.jar"));
+ args.add(Arguments.of("jar:file:///path/to/bar.jar", "jar:file:///path/to/bar.jar"));
+
+ return args.stream();
+ }
+
+ @ParameterizedTest
+ @MethodSource("toURICases")
+ public void testToURI(String inputRaw, String expectedUri)
+ {
+ URI actual = URIUtil.toURI(inputRaw);
+ URI expected = URI.create(expectedUri);
+ assertEquals(expected, actual);
+ }
+
@Test
public void testSplitSingleJar()
{
diff --git a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/AttributeNormalizerTest.java b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/AttributeNormalizerTest.java
index 89434af6509..e07cd7062d6 100644
--- a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/AttributeNormalizerTest.java
+++ b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/AttributeNormalizerTest.java
@@ -13,6 +13,7 @@
package org.eclipse.jetty.util.resource;
+import java.io.File;
import java.io.IOException;
import java.net.URI;
import java.nio.file.Files;
@@ -335,13 +336,13 @@ public class AttributeNormalizerTest
assertThat(normalizer.expand("${WAR.uri}/file1"), containsString("/dir1/file1"));
assertThat(normalizer.expand("${WAR.uri}/file2"), containsString("/dir2/file2"));
assertThat(normalizer.expand("${WAR.uri}/file3"), containsString("/dir3/file3"));
- assertThat(normalizer.expand("${WAR.path}/file1"), containsString("/dir1/file1"));
- assertThat(normalizer.expand("${WAR.path}/file2"), containsString("/dir2/file2"));
- assertThat(normalizer.expand("${WAR.path}/file3"), containsString("/dir3/file3"));
+ assertThat(normalizer.expand("${WAR.path}/file1"), containsString(FS.separators("/dir1/file1")));
+ assertThat(normalizer.expand("${WAR.path}/file2"), containsString(FS.separators("/dir2/file2")));
+ assertThat(normalizer.expand("${WAR.path}/file3"), containsString(FS.separators("/dir3/file3")));
// If file cannot be found it just uses the first resource.
assertThat(normalizer.expand("${WAR.uri}/file4"), containsString("/dir1/file4"));
- assertThat(normalizer.expand("${WAR.path}/file4"), containsString("/dir1/file4"));
+ assertThat(normalizer.expand("${WAR.path}/file4"), containsString(File.separator + "dir1/file4"));
}
public static class Scenario
diff --git a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/CombinedResourceTest.java b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/CombinedResourceTest.java
index fb586088fed..f45c7a0ee9e 100644
--- a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/CombinedResourceTest.java
+++ b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/CombinedResourceTest.java
@@ -110,9 +110,9 @@ public class CombinedResourceTest
.toList();
expected = new String[] {
- "dir/1.txt",
- "dir/2.txt",
- "dir/3.txt"
+ FS.separators("dir/1.txt"),
+ FS.separators("dir/2.txt"),
+ FS.separators("dir/3.txt")
};
assertThat(relative, containsInAnyOrder(expected));
@@ -281,9 +281,9 @@ public class CombinedResourceTest
"2.txt",
"3.txt",
"4.txt",
- "dir/1.txt",
- "dir/2.txt",
- "dir/3.txt"
+ FS.separators("dir/1.txt"),
+ FS.separators("dir/2.txt"),
+ FS.separators("dir/3.txt")
};
assertThat(actual, contains(expected));
@@ -804,9 +804,9 @@ public class CombinedResourceTest
"2.txt",
"3.txt",
"dir",
- "dir/1.txt",
- "dir/2.txt",
- "dir/3.txt"
+ FS.separators("dir/1.txt"),
+ FS.separators("dir/2.txt"),
+ FS.separators("dir/3.txt")
));
}
diff --git a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/FileSystemResourceTest.java b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/FileSystemResourceTest.java
index c3aa50f5345..ab89e145738 100644
--- a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/FileSystemResourceTest.java
+++ b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/FileSystemResourceTest.java
@@ -172,14 +172,16 @@ public class FileSystemResourceTest
Files.createDirectories(testdir);
Path pwd = Paths.get(System.getProperty("user.dir"));
- Path relativePath = pwd.relativize(testdir);
+
+ // Establish a relative path URI that uses uri "/" path separators (now windows "\")
+ URI relativePath = pwd.toUri().relativize(testdir.toUri());
// Get a path relative name using unix/uri "/" (not windows "\")
- String relativeName = FS.separators(relativePath.toString());
- assertThat("Should not have path navigation entries", relativeName, not(containsString("..")));
+ assertThat("Should not have path navigation entries", relativePath.toASCIIString(), not(containsString("..")));
+ assertFalse(relativePath.isAbsolute());
- resource = ResourceFactory.root().newResource(new URI(relativeName));
- assertThat("Relative newResource: " + relativeName, resource, notNullValue());
+ resource = ResourceFactory.root().newResource(relativePath);
+ assertThat("Relative newResource: " + relativePath, resource, notNullValue());
assertThat(resource.getURI().toString(), startsWith("file:"));
assertThat(resource.getURI().toString(), endsWith("/path/to/resource/"));
}
@@ -1095,7 +1097,8 @@ public class FileSystemResourceTest
if (WINDOWS.isCurrentOs())
{
- assertThat("getURI()", r.getPath().toString(), containsString("aa\\/foo.txt"));
+ // On windows, the extra "\" is stripped when working with java.nio.Path objects
+ assertThat("getURI()", r.getPath().toString(), containsString("aa\\foo.txt"));
assertThat("getURI()", r.getURI().toASCIIString(), containsString("aa%5C/foo.txt"));
assertThat("isAlias()", r.isAlias(), is(true));
assertThat("getRealURI()", r.getRealURI(), notNullValue());
@@ -1279,7 +1282,16 @@ public class FileSystemResourceTest
Resource r = base.resolve("file.txt");
assertThat("Exists: " + r, r.exists(), is(true));
- assertThat("Is Not Alias: " + r, r, isNotAlias());
+ if (WINDOWS.isCurrentOs())
+ {
+ // On windows, the base.resolve results in a representation of ".../testUtf8Dir/b%C3%A3m/file.txt"
+ // But that differs from the input URI of ".../testUtf8Dir/bãm/file.txt", so it is viewed as an alias.
+ assertThat("Is Alias: " + r, r, isAlias());
+ URI realURI = r.getRealURI();
+ assertThat(realURI, is(file.toUri()));
+ }
+ else
+ assertThat("Is Not Alias: " + r, r, isNotAlias());
}
@Test
@@ -1287,6 +1299,7 @@ public class FileSystemResourceTest
public void testUncPath()
{
Resource base = ResourceFactory.root().newResource(URI.create("file:////127.0.0.1/path"));
+ assumeTrue(base != null);
Resource resource = base.resolve("WEB-INF/");
assertThat("getURI()", resource.getURI().toASCIIString(), containsString("path/WEB-INF/"));
assertThat("isAlias()", resource.isAlias(), is(false));
diff --git a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/PathResourceTest.java b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/PathResourceTest.java
index 24f85ac3e89..a183776aec6 100644
--- a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/PathResourceTest.java
+++ b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/PathResourceTest.java
@@ -38,6 +38,7 @@ import org.eclipse.jetty.util.URIUtil;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
+import org.junit.jupiter.api.condition.OS;
import org.junit.jupiter.api.extension.ExtendWith;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@@ -736,8 +737,21 @@ public class PathResourceTest
{
Path testDir = workDir.getEmptyPathDir();
Path resourcePath = testDir.resolve("resource.txt");
+ Path symlinkPath = null;
IO.copy(MavenTestingUtils.getTestResourcePathFile("resource.txt").toFile(), resourcePath.toFile());
- Path symlinkPath = Files.createSymbolicLink(testDir.resolve("symlink.txt"), resourcePath);
+ boolean symlinkSupported;
+ try
+ {
+ symlinkPath = Files.createSymbolicLink(testDir.resolve("symlink.txt"), resourcePath);
+ symlinkSupported = true;
+ }
+ catch (UnsupportedOperationException | FileSystemException e)
+ {
+ symlinkSupported = false;
+ }
+
+ assumeTrue(symlinkSupported, "Symlink not supported");
+ assertNotNull(symlinkPath);
PathResource fileResource = new PathResource(resourcePath);
assertTrue(fileResource.exists());
@@ -786,7 +800,10 @@ public class PathResourceTest
Resource rootRes = resourceFactory.newResource(docroot);
// Test navigation through a directory that doesn't exist
Resource fileResViaBar = rootRes.resolve("bar/../dir/test.txt");
- assertTrue(Resources.missing(fileResViaBar));
+ if (OS.WINDOWS.isCurrentOs()) // windows allows navigation through a non-existent directory
+ assertTrue(Resources.exists(fileResViaBar));
+ else
+ assertTrue(Resources.missing(fileResViaBar));
// Test navigation through a directory that does exist
Resource fileResViaFoo = rootRes.resolve("foo/../dir/test.txt");
diff --git a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/ResourceAliasTest.java b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/ResourceAliasTest.java
index c49e3e4e632..c6a97baaf58 100644
--- a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/ResourceAliasTest.java
+++ b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/ResourceAliasTest.java
@@ -25,6 +25,7 @@ import org.eclipse.jetty.toolchain.test.jupiter.WorkDirExtension;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
+import org.junit.jupiter.api.condition.OS;
import org.junit.jupiter.api.extension.ExtendWith;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@@ -73,7 +74,10 @@ public class ResourceAliasTest
Resource rootRes = resourceFactory.newResource(docroot);
// Test navigation through a directory that doesn't exist
Resource fileResViaBar = rootRes.resolve("bar/../dir/test.txt");
- assertTrue(Resources.missing(fileResViaBar), "File doesn't exist");
+ if (OS.WINDOWS.isCurrentOs()) // windows allows navigation through a non-existent directory
+ assertTrue(Resources.exists(fileResViaBar));
+ else
+ assertTrue(Resources.missing(fileResViaBar), "File doesn't exist");
// Test navigation through a directory that does exist
Resource fileResViaFoo = rootRes.resolve("foo/../dir/test.txt");
diff --git a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/ResourceFactoryTest.java b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/ResourceFactoryTest.java
index ab833cd01ca..b0781a62c3c 100644
--- a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/ResourceFactoryTest.java
+++ b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/ResourceFactoryTest.java
@@ -135,16 +135,15 @@ public class ResourceFactoryTest
// Try this as a normal String input first.
// We are subject to the URIUtil.toURI(String) behaviors here.
// Since the `ftp` scheme is not registered, it's not recognized as a supported URI.
- // This will be treated as a relative path instead. (and the '//' will be compacted)
- Resource resource = ResourceFactory.root().newResource("ftp://webtide.com/favicon.ico");
- // Should not find this, as it doesn't exist on the filesystem.
- assertNull(resource);
+ IllegalArgumentException iae = assertThrows(IllegalArgumentException.class,
+ () -> ResourceFactory.root().newResource("ftp://webtide.com/favicon.ico"));
+ assertThat(iae.getMessage(), containsString("URI scheme not registered: ftp"));
// Now try it as a formal URI object as input.
URI uri = URI.create("ftp://webtide.com/favicon.ico");
// This is an unsupported URI scheme
- IllegalArgumentException iae = assertThrows(IllegalArgumentException.class, () -> ResourceFactory.root().newResource(uri));
- assertThat(iae.getMessage(), containsString("URI scheme not supported"));
+ iae = assertThrows(IllegalArgumentException.class, () -> ResourceFactory.root().newResource(uri));
+ assertThat(iae.getMessage(), containsString("URI scheme not registered: ftp"));
}
@Test
diff --git a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/ResourceTest.java b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/ResourceTest.java
index bdddb610385..e690b8ee9df 100644
--- a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/ResourceTest.java
+++ b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/ResourceTest.java
@@ -434,7 +434,17 @@ public class ResourceTest
Resource resource = resourceFactory.newResource(file);
// Requesting a resource that would point to a location called ".../testDotAliasFileExists/foo/bar.txt/."
Resource dot = resource.resolve(".");
- assertTrue(Resources.missing(dot), "Cannot reference file as a directory");
+ if (OS.WINDOWS.isCurrentOs())
+ {
+ // windows allows this reference, but it's an alias.
+ assertTrue(Resources.exists(dot), "Reference to directory via dot allowed");
+ assertTrue(dot.isAlias(), "Reference to dot is an alias to actual bar.txt");
+ assertEquals(dot.getRealURI(), file.toUri());
+ }
+ else
+ {
+ assertTrue(Resources.missing(dot), "Cannot reference file as a directory");
+ }
}
@Test
diff --git a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/UrlResourceFactoryTest.java b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/UrlResourceFactoryTest.java
index 36037417d46..7f028f4b5a9 100644
--- a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/UrlResourceFactoryTest.java
+++ b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/resource/UrlResourceFactoryTest.java
@@ -274,7 +274,7 @@ public class UrlResourceFactoryTest
assertThat("resource /path/to/example.jar/WEB-INF/web.xml doesn't exist", webResource.exists(), is(false));
assertThat(webResource.isDirectory(), is(false));
- URI expectedURI = URIUtil.correctFileURI(URI.create("file:" + path.toUri().toASCIIString() + "/WEB-INF/web.xml"));
+ URI expectedURI = URIUtil.correctURI(URI.create("file:" + path.toUri().toASCIIString() + "/WEB-INF/web.xml"));
assertThat(webResource.getURI(), is(expectedURI));
}
@@ -296,7 +296,7 @@ public class UrlResourceFactoryTest
assertThat("resource /path/to/example.jar/WEB-INF/web.xml doesn't exist", webResource.exists(), is(false));
assertThat(webResource.isDirectory(), is(false));
- URI expectedURI = URIUtil.correctFileURI(URI.create(path.toUri().toASCIIString() + "/WEB-INF/web.xml"));
+ URI expectedURI = URIUtil.correctURI(URI.create(path.toUri().toASCIIString() + "/WEB-INF/web.xml"));
assertThat(webResource.getURI(), is(expectedURI));
}
diff --git a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/ssl/SslContextFactoryTest.java b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/ssl/SslContextFactoryTest.java
index 23c8d914676..c4a77082d1f 100644
--- a/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/ssl/SslContextFactoryTest.java
+++ b/jetty-core/jetty-util/src/test/java/org/eclipse/jetty/util/ssl/SslContextFactoryTest.java
@@ -43,6 +43,8 @@ import org.eclipse.jetty.util.component.AbstractLifeCycle;
import org.eclipse.jetty.util.resource.Resource;
import org.eclipse.jetty.util.resource.ResourceFactory;
import org.junit.jupiter.api.Test;
+import org.junit.jupiter.api.condition.DisabledOnOs;
+import org.junit.jupiter.api.condition.OS;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.containsInAnyOrder;
@@ -381,6 +383,7 @@ public class SslContextFactoryTest
}
@Test
+ @DisabledOnOs(value = OS.WINDOWS, disabledReason = "Will result in java.net.SocketException: An established connection was aborted by the software in your host machine during IO.readBytes(input)")
public void testSNIWithPKIX() throws Exception
{
SslContextFactory.Server serverTLS = new SslContextFactory.Server()
diff --git a/jetty-ee10/jetty-ee10-webapp/src/test/java/org/eclipse/jetty/ee10/webapp/MetaInfConfigurationTest.java b/jetty-ee10/jetty-ee10-webapp/src/test/java/org/eclipse/jetty/ee10/webapp/MetaInfConfigurationTest.java
index 6cf334c03ef..3d54cf02593 100644
--- a/jetty-ee10/jetty-ee10-webapp/src/test/java/org/eclipse/jetty/ee10/webapp/MetaInfConfigurationTest.java
+++ b/jetty-ee10/jetty-ee10-webapp/src/test/java/org/eclipse/jetty/ee10/webapp/MetaInfConfigurationTest.java
@@ -562,8 +562,8 @@ public class MetaInfConfigurationTest
// we "correct" the bad file URLs that come from the ClassLoader
// to be the same as what comes from every non-classloader URL/URI.
String[] expectedContainerResources = {
- URIUtil.correctFileURI(janbUri).toASCIIString(),
- URIUtil.correctFileURI(servletUri).toASCIIString()
+ URIUtil.correctURI(janbUri).toASCIIString(),
+ URIUtil.correctURI(servletUri).toASCIIString()
};
assertThat("Discovered Container resources", discoveredContainerResources, hasItems(expectedContainerResources));
}