Apply fallback resolution for non-hierarchical URIs such as "file:."

Includes meaningful exception message for file system resolution.

Closes gh-33124
This commit is contained in:
Juergen Hoeller 2024-07-03 16:36:18 +02:00
parent 8974da2a5a
commit daea3f0eae
3 changed files with 36 additions and 10 deletions

View File

@ -1,5 +1,5 @@
/* /*
* Copyright 2002-2023 the original author or authors. * Copyright 2002-2024 the original author or authors.
* *
* Licensed under the Apache License, Version 2.0 (the "License"); * Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License. * you may not use this file except in compliance with the License.
@ -92,9 +92,9 @@ public class PathEditor extends PropertyEditorSupport {
// a file prefix (let's try as Spring resource location) // a file prefix (let's try as Spring resource location)
nioPathCandidate = !text.startsWith(ResourceUtils.FILE_URL_PREFIX); nioPathCandidate = !text.startsWith(ResourceUtils.FILE_URL_PREFIX);
} }
catch (FileSystemNotFoundException ex) { catch (FileSystemNotFoundException | IllegalArgumentException ex) {
// URI scheme not registered for NIO (let's try URL // URI scheme not registered for NIO or not meeting Paths requirements:
// protocol handlers via Spring's resource mechanism). // let's try URL protocol handlers via Spring's resource mechanism.
} }
} }
@ -111,8 +111,13 @@ public class PathEditor extends PropertyEditorSupport {
setValue(resource.getFile().toPath()); setValue(resource.getFile().toPath());
} }
catch (IOException ex) { catch (IOException ex) {
throw new IllegalArgumentException( String msg = "Could not resolve \"" + text + "\" to 'java.nio.file.Path' for " + resource + ": " +
"Could not retrieve file for " + resource + ": " + ex.getMessage()); ex.getMessage();
if (nioPathCandidate) {
msg += " - In case of ambiguity, consider adding the 'file:' prefix for an explicit reference " +
"to a file system resource of the same name: \"file:" + text + "\"";
}
throw new IllegalArgumentException(msg);
} }
} }
} }

View File

@ -46,9 +46,9 @@ class FileEditorTests {
@Test @Test
void testWithNonExistentResource() { void testWithNonExistentResource() {
PropertyEditor propertyEditor = new FileEditor(); PropertyEditor fileEditor = new FileEditor();
assertThatIllegalArgumentException().isThrownBy(() -> assertThatIllegalArgumentException().isThrownBy(() ->
propertyEditor.setAsText("classpath:no_way_this_file_is_found.doc")); fileEditor.setAsText("classpath:no_way_this_file_is_found.doc"));
} }
@Test @Test
@ -71,6 +71,16 @@ class FileEditorTests {
assertThat(file).doesNotExist(); assertThat(file).doesNotExist();
} }
@Test
void testCurrentDirectory() {
PropertyEditor fileEditor = new FileEditor();
fileEditor.setAsText("file:.");
Object value = fileEditor.getValue();
assertThat(value).isInstanceOf(File.class);
File file = (File) value;
assertThat(file).isEqualTo(new File("."));
}
@Test @Test
void testUnqualifiedFileNameFound() { void testUnqualifiedFileNameFound() {
PropertyEditor fileEditor = new FileEditor(); PropertyEditor fileEditor = new FileEditor();

View File

@ -19,6 +19,7 @@ package org.springframework.beans.propertyeditors;
import java.beans.PropertyEditor; import java.beans.PropertyEditor;
import java.io.File; import java.io.File;
import java.nio.file.Path; import java.nio.file.Path;
import java.nio.file.Paths;
import org.junit.jupiter.api.Test; import org.junit.jupiter.api.Test;
@ -46,9 +47,9 @@ class PathEditorTests {
@Test @Test
void testWithNonExistentResource() { void testWithNonExistentResource() {
PropertyEditor propertyEditor = new PathEditor(); PropertyEditor pathEditor = new PathEditor();
assertThatIllegalArgumentException().isThrownBy(() -> assertThatIllegalArgumentException().isThrownBy(() ->
propertyEditor.setAsText("classpath:/no_way_this_file_is_found.doc")); pathEditor.setAsText("classpath:/no_way_this_file_is_found.doc"));
} }
@Test @Test
@ -98,6 +99,16 @@ class PathEditorTests {
} }
} }
@Test
void testCurrentDirectory() {
PropertyEditor pathEditor = new PathEditor();
pathEditor.setAsText("file:.");
Object value = pathEditor.getValue();
assertThat(value).isInstanceOf(Path.class);
Path path = (Path) value;
assertThat(path).isEqualTo(Paths.get("."));
}
@Test @Test
void testUnqualifiedPathNameFound() { void testUnqualifiedPathNameFound() {
PropertyEditor pathEditor = new PathEditor(); PropertyEditor pathEditor = new PathEditor();