Class FileTools
-
Field Summary
FieldsModifier and TypeFieldDescriptionstatic final DirectoryStream.Filter<Path> static final DirectoryStream.Filter<Path> -
Method Summary
Modifier and TypeMethodDescriptionstatic StringadaptPathForWindows(String path) adaptPathForWindows.static booleancheckPathExistance(Path path, boolean create) checkPathExistance.static voidcompressGzipFile(File file, File gzipFile) compressGzipFile.static voidcompressZip(OutputStream output, Map<Path, String> contentMap, Integer level) compressZipFile.static voidcompressZipFile(List<File> files, File zipFile, Integer level) compressZipFile.static voidcompressZipFile.static voidcopyRejectingSymlinks(InputStream source, Path targetFile) Convenience overload without size limit.static voidcopyRejectingSymlinks(InputStream source, Path targetFile, long maxBytes) Copies bytes from the given input stream to the given target file (replacing it if it exists), but refuses to follow symbolic links at the target path or its immediate parent directory.static voidcopyStream(OutputStream output, InputStream input) copyStream.static voiddecompressGzipFile(File gzipFile, File newFile) decompressGzipFile.static StringgetBottomFolderFromPathString(String pathString) Parses the given String asPathand returns the lowest folder name as String.static StringgetCharset(Path file) static FileTimegetDateCreated(Path path) static FileTimegetDateModified(Path path) static FilegetFileFromString(String string, String filePath, String encoding, boolean append) Simply write a String into a text file.static StringgetFilenameFromPathString(String pathString) Parses the given String asPathand returns the last path element (the filename) as String.static StringgetMimeTypeFromFile(Path path) static PathgetPathFromUrlString(String urlString) Creates a Path from the given URL in a way that word on Windows machines.static StringgetStringFromByteArray(byte[] bytes, String encoding) Reads a String from a byte array.static StringgetStringFromFile(File file, String encoding) Reads a text file and return content as String.static StringgetStringFromFile(File file, String encoding, String convertToEncoding) Reads a text file and return content as String.static StringgetStringFromFilePath(String filePath) getStringFromFilePath.static booleanisFolderEmpty(Path folder) isFolderEmpty.static booleanCheck if a path is a real descendant of the parent path.static booleanisYoungerThan(Path path, Path reference) listFiles(Path folder, DirectoryStream.Filter<Path> filter) static PathmoveRejectingSymlinks(Path source, Path target, CopyOption... options) Moves a file, refusing to follow symbolic links at the source, target, or either parent.static BufferedWriternewBufferedWriterRejectingSymlinks(Path targetFile) Opens aBufferedWriteron the given path with UTF-8 encoding, refusing to follow symbolic links at the target path or its parent.static InputStreamopenRejectingSymlinks(Path sourceFile) Opens anInputStreamon the given regular file, refusing to follow symbolic links at the target path or its immediate parent directory.static StringprobeContentType(String content) Guess the content type of the given text, usingURLConnection.guessContentTypeFromName(String)If no content type could be determined, 'text/plain' is assumed.static StringprobeContentType(URI uri) Guess the content type (mimeType) of the resource found at the given uri.static PathreplaceExtension(Path path, String extension) Returns a path which equals the given path but using the given extension in place of the original one.static StringsanitizeFileName(String fileName) Removes any path elements from the given file name.
-
Field Details
-
IMAGE_NAME_FILTER
-
PDF_NAME_FILTER
-
-
Method Details
-
getStringFromFilePath
getStringFromFilePath.- Parameters:
filePath- absolute or relative path to the file- Returns:
- the complete file content as a string
- Throws:
IOException- if any.
-
getStringFromFile
Reads a text file and return content as String.- Parameters:
file- text file to readencoding- The character encoding to use. If null, a standard utf-8 encoding will be used- Returns:
- the complete file content as a trimmed string
- Throws:
IOException- if any.
-
getStringFromFile
public static String getStringFromFile(File file, String encoding, String convertToEncoding) throws IOException Reads a text file and return content as String.- Parameters:
file- text file to readencoding- The character encoding to use. If null, a standard utf-8 encoding will be usedconvertToEncoding- Optional target encoding for conversion- Returns:
- the complete file content as a trimmed string, optionally re-encoded
- Throws:
IOException- if any.
-
getCharset
- Parameters:
file- Path to the file whose charset should be detected- Returns:
- Charset of the given file
- Throws:
IOException
-
getStringFromByteArray
Reads a String from a byte array.- Parameters:
bytes- raw byte array to read as textencoding- character encoding to apply when reading bytes- Returns:
- the string decoded from the given byte array using the specified encoding
-
getFileFromString
public static File getFileFromString(String string, String filePath, String encoding, boolean append) throws IOException Simply write a String into a text file.- Parameters:
string- The String to writefilePath- The file path to write to (will be created if it doesn't exist)encoding- The character encoding to use. If null, a standard utf-8 encoding will be usedappend- Whether to append the text to an existing file (true), or to overwrite it (false)- Returns:
- the written file
- Throws:
IOException- if any.
-
decompressGzipFile
decompressGzipFile.- Parameters:
gzipFile- compressed source file to decompressnewFile- destination file for the decompressed content- Throws:
IOException- if any.
-
compressGzipFile
compressGzipFile.- Parameters:
file- source file to compressgzipFile- target file to write the compressed output to- Throws:
IOException- if any.
-
compressZipFile
public static void compressZipFile(List<File> files, File zipFile, Integer level) throws IOException compressZipFile.- Parameters:
files- Source fileszipFile- Target filelevel- The compression level of the zip archive. Must be an integer in the range from 0 to 9- Throws:
IOException- if any.
-
compressZipFile
public static void compressZipFile(Map<Path, String> contentMap, File zipFile, Integer level) throws IOExceptioncompressZipFile.- Parameters:
contentMap- map of entry paths to their text contentzipFile- target ZIP file to writelevel- The compression level of the zip archive. Must be an integer in the range from 0 to 9- Throws:
IOException- if any.
-
compressZip
public static void compressZip(OutputStream output, Map<Path, String> contentMap, Integer level) throws IOExceptioncompressZipFile.- Parameters:
output- OutputStream to write the ZIP data intocontentMap- map of entry paths to their text contentlevel- The compression level of the zip archive. Must be an integer in the range from 0 to 9- Throws:
IOException- if any.
-
checkPathExistance
checkPathExistance.- Parameters:
path- filesystem path to check for existencecreate- true to create the directory if it does not exist- Returns:
- true if the path exists (or was successfully created), false otherwise
- Throws:
IOException- if any.
-
copyStream
copyStream.- Parameters:
output- destination stream to write bytes toinput- source stream to read bytes from- Throws:
IOException- if any.
-
isFolderEmpty
isFolderEmpty.- Parameters:
folder- directory path to check for contents- Returns:
- true if folder empty; false otherwise
- Throws:
IOException- if any.
-
adaptPathForWindows
adaptPathForWindows.- Parameters:
path- Absolute path to adapt- Returns:
- Windows-compatible path on Windows; unchanged path elsewhere
-
probeContentType
Guess the content type (mimeType) of the resource found at the given uri. Content type if primarily guessed from the file extension of the last url path part. If that type is 'text/plain' further analysis is done using the actual content to determine if the actual type is html or xml If the type could not be determined from the file extension, the url response header is probed to return its 'Content-type'- Parameters:
uri- uri of the resource. May be a file uri, a relative uri (then assumed to be a relative file path) or a http(s) uri- Returns:
- The most likely mimeType of the resource found at the given uri
- Throws:
IOException
-
getMimeTypeFromFile
- Throws:
IOException
-
probeContentType
Guess the content type of the given text, usingURLConnection.guessContentTypeFromName(String)If no content type could be determined, 'text/plain' is assumed.- Parameters:
content- Text content whose MIME type should be guessed- Returns:
- Content mime type
-
getBottomFolderFromPathString
Parses the given String asPathand returns the lowest folder name as String. Returns an empty String if the given path is empty or null- Parameters:
pathString- Path string from which to extract the parent folder name- Returns:
- The folder name, or an empty String if it could not be determined
-
getFilenameFromPathString
Parses the given String asPathand returns the last path element (the filename) as String. Returns an empty String if the given path is empty or null- Parameters:
pathString- Path or URL string from which to extract the file name- Returns:
- The filename, or an empty String if it could not be determined
- Throws:
FileNotFoundException
-
getPathFromUrlString
Creates a Path from the given URL in a way that word on Windows machines.- Parameters:
urlString- Relative or absolute path or URL, with or without protocol. If a URL parameter is in itself a complete URL, it must be escaped first!- Returns:
- Constructed Path
-
listFiles
-
replaceExtension
Returns a path which equals the given path but using the given extension in place of the original one.- Parameters:
path- any file pathextension- the extension, without leading '.'- Returns:
- Given path with replaced file extension
-
isWithin
Check if a path is a real descendant of the parent path.- Parameters:
path- Path to check for containment within parentparent- Ancestor path that should contain path- Returns:
- true if path is a descendant of parent, first resolving any path backtracking with '../' or similar
-
isYoungerThan
-
getDateCreated
- Throws:
IOException
-
getDateModified
- Throws:
IOException
-
sanitizeFileName
Removes any path elements from the given file name.- Parameters:
fileName- File name or path to sanitize- Returns:
- Lowest level file name
-
copyRejectingSymlinks
Convenience overload without size limit. Delegates tocopyRejectingSymlinks(InputStream, Path, long)withmaxBytes = -1(unlimited).- Parameters:
source- input stream of bytes to write; not closed by this methodtargetFile- target file path to write to- Throws:
IOException- iftargetFileor its parent is a symbolic link, if the target is a directory, or if the write fails
-
copyRejectingSymlinks
public static void copyRejectingSymlinks(InputStream source, Path targetFile, long maxBytes) throws IOException Copies bytes from the given input stream to the given target file (replacing it if it exists), but refuses to follow symbolic links at the target path or its immediate parent directory. IfmaxBytesis positive the copy is aborted as soon as the byte count exceeds the limit, the partial file is deleted, and anIOExceptionis thrown.Defense-in-depth against symlink-based file overwrite attacks (CWE-59 / OWASP A05) and unbounded uploads (DoS via disk exhaustion). The target file is opened via
FileChannel.open(Path, java.nio.file.OpenOption...)withLinkOption.NOFOLLOW_LINKS, so the operating system rejects the open if the leaf path element is a symbolic link (Linux:O_NOFOLLOW). The parent directory is checked separately viaFiles.isSymbolicLink(Path)becauseNOFOLLOW_LINKSonly constrains the last path element.The input stream is not closed by this method, matching the semantics of
Files.copy(InputStream, Path, java.nio.file.CopyOption...); the caller is responsible for closing it.- Parameters:
source- input stream of bytes to write; not closed by this methodtargetFile- target file path to write tomaxBytes- maximum number of bytes allowed;<= 0means unlimited- Throws:
IOException- iftargetFileor its parent is a symbolic link, if the target is a directory, if the input exceedsmaxBytes, or if the write itself fails
-
openRejectingSymlinks
Opens anInputStreamon the given regular file, refusing to follow symbolic links at the target path or its immediate parent directory. Defence-in-depth against symlink-based file exfiltration (CWE-59).The file is opened via
FileChannel.open(Path, java.nio.file.OpenOption...)withLinkOption.NOFOLLOW_LINKS, which on Linux maps to theO_NOFOLLOWopen flag. The parent directory is checked separately becauseNOFOLLOW_LINKSonly constrains the leaf path element.Caller is responsible for closing the returned stream. Closing it also closes the underlying
FileChannel(seeChannels.newInputStream(java.nio.channels.ReadableByteChannel)).- Parameters:
sourceFile- regular file to read- Returns:
- a fresh
InputStreambacked by a NOFOLLOW-openedFileChannel - Throws:
IOException- ifsourceFileor its parent is a symbolic link, if the file is missing, or if open fails
-
moveRejectingSymlinks
public static Path moveRejectingSymlinks(Path source, Path target, CopyOption... options) throws IOException Moves a file, refusing to follow symbolic links at the source, target, or either parent. Defence-in-depth against symlink-based file overwrite (CWE-59).Both endpoints are pre-checked with
Files.isSymbolicLink(java.nio.file.Path);Files.move(java.nio.file.Path, java.nio.file.Path, java.nio.file.CopyOption...)does not acceptLinkOption.NOFOLLOW_LINKSas aCopyOption(onlyREPLACE_EXISTING,ATOMIC_MOVE,COPY_ATTRIBUTES), so the pre-check is the practical mitigation. A residual TOCTOU race between the pre-check and the move itself is acknowledged — see audit memo FS-SYMLINK-READ.Hard links at the source are intentionally not detected (out of scope).
- Parameters:
source- existing source pathtarget- target pathoptions- copy options forwarded toFiles.move(java.nio.file.Path, java.nio.file.Path, java.nio.file.CopyOption...)- Returns:
- the path returned by
Files.move(java.nio.file.Path, java.nio.file.Path, java.nio.file.CopyOption...) - Throws:
IOException- if source, target, or either parent is a symbolic link
-
newBufferedWriterRejectingSymlinks
Opens aBufferedWriteron the given path with UTF-8 encoding, refusing to follow symbolic links at the target path or its parent. Truncates an existing file; creates one if it does not exist. Defence-in-depth against symlink-based file overwrite (CWE-59).The file is opened via
FileChannel.open(Path, java.nio.file.OpenOption...)withWRITE,CREATE,TRUNCATE_EXISTINGandLinkOption.NOFOLLOW_LINKS. Parent symlinks are rejected separately.Caller is responsible for closing the returned writer. Closing it also closes the underlying
FileChannel.- Parameters:
targetFile- target file path- Returns:
- a
BufferedWriterwrapping a NOFOLLOW-openedFileChannelwith UTF-8 encoding - Throws:
IOException- iftargetFileor its parent is a symbolic link, or open fails
-