Ошибка чтения пути paths.get() java
получаю вот такую ошибку при использовании paths. Ссылку получаю из БД postgre. Не могу понять, что не так с ссылкой.
java.nio.file.InvalidPathException: Illegal char <:> at index 4: http://localhost:8080/download/2QkQNYMM84w.jpg
Вот сам код.
@PostMapping("/update-picture")
@ResponseStatus
public FileResponse updatePicture(@RequestParam("file") MultipartFile multipartFile, HttpServletRequest request)
{
UserEntity user = userService.findByLogin(jwtProvider.getLoginFromToken(request.getHeader("Authorization")));
Path path = Paths.get(user.getUrl_picture().trim());
storageService.delete(path.getFileName().toString());
return uploadFile(multipartFile,request);
}
Ответы (1 шт):
Судя по всему, трюк с Paths.get для получения имени файла из адреса работает не везде. Под Windows, класс, отвечающий за файловую систему, sun.nio.fs.WindowsPathParser проверяет, что в пути указан максимум один однобуквенный диск в начале строки и что в остальной строке нет двоеточия.
Не рекомендую усугублять ситуацию и пытаться подстроить веб-адрес под требования Paths.get. Лучше выберите другой способ определения имени файла. Множество таких способов можно найти в таком же вопросе на английском: Get file name from URL.
Самый популярный ответ предлагает подключить Apache Commons (commons-io):
String filename = FilenameUtils.getName(user.getUrl_picture().trim());
storageService.delete(filename);
Вроде бы это работает, хотя FilenameUtils тоже предназначен для файловой системы. Протестируйте повнимательнее случай адресов с GET параметрами.
Дополнение: «Хорошего» класса, предназначенного именно для URL, решающего эту задачу, я так сразу не нашел. Если FilenameUtils по каким-то причинам не сработает, то можно пойти на крайние меры, а именно на регулярное выражение:
/**
* Регулярное выражение для выделения имени файла из URL.
* <p>
* Найдено на
* <a href="https://stackoverflow.com/questions/14473180/regex-to-get-a-filename-from-a-url#26253039">Stack
* Overflow</a>
* <p>
* Разбор:
* <ul>
* <li>[^/\\&\?]+ - имя файла (любой набор символов кроме /, \, & и ?)
* <li>.\\w{1,5} - расширение (от одной до пяти букв)
* <li>(?=([\?&].*$|$)) - проверка что после файла либо конец строки, либо
* GET-параметры.
* </ul>
*/
private static final Pattern FILENAME_PATTERN = Pattern.compile("[^/\\\\&\\?]+\\.\\w{1,5}(?=([\\?&].*$|$))");
/**
* Выделяет имя файла из URL
*
* @param path - строка URL
* @return имя файла
*/
private static String getFilename(String path) {
Matcher matcher = FILENAME_PATTERN.matcher(path);
if (!matcher.find()) {
throw new IllegalArgumentException("Couldn't find a filename in a path: " + path);
}
return matcher.group();
}