001// Generated by delombok at Sat Feb 25 17:58:34 UTC 2023 002package io.cui.tools.io; 003 004import static io.cui.tools.string.MoreStrings.isEmpty; 005import static java.util.Objects.requireNonNull; 006import java.io.IOException; 007import java.io.InputStream; 008import java.io.OutputStream; 009import java.net.MalformedURLException; 010import java.net.URL; 011import java.nio.file.Files; 012import java.nio.file.Path; 013import java.nio.file.Paths; 014import io.cui.tools.base.Preconditions; 015import io.cui.tools.logging.CuiLogger; 016import io.cui.tools.string.MoreStrings; 017 018/** 019 * File-system based variant. Responsible for all non {@link FileTypePrefix#CLASSPATH} files. 020 * 021 * @author Oliver Wolff 022 */ 023public class FileSystemLoader implements FileReaderWriter { 024 private static final long serialVersionUID = -1278929108857440808L; 025 private static final CuiLogger LOG = new CuiLogger(FileSystemLoader.class); 026 private final String normalizedPathName; 027 private final boolean readable; 028 private final boolean writable; 029 private final StructuredFilename fileName; 030 031 /** 032 * @param pathName must not be null nor empty, must not start with the prefix 033 * "classpath:" but may start with the prefix 034 * "file:" and contain at least one character despite the prefix. On all other cases 035 * a {@link IllegalArgumentException} will be 036 * thrown. 037 */ 038 public FileSystemLoader(final String pathName) { 039 requireNonNull(pathName); 040 normalizedPathName = checkPathName(pathName); 041 Preconditions.checkArgument(!isEmpty(normalizedPathName), "\'%s\' can not be normalized", pathName); 042 final var path = getPath(); 043 readable = MorePaths.checkReadablePath(path, false, true); 044 writable = MorePaths.checkAccessiblePath(path, false, false); 045 fileName = new StructuredFilename(path.toAbsolutePath().getFileName().toString()); 046 } 047 048 /** 049 * Variant that uses a path as the constructor argument 050 * 051 * @param path must not be null 052 */ 053 public FileSystemLoader(final Path path) { 054 this(requireNonNull(path).toFile().getAbsolutePath()); 055 } 056 057 /** 058 * @return the path 059 */ 060 public Path getPath() { 061 return Paths.get(normalizedPathName); 062 } 063 064 @Override 065 public InputStream inputStream() throws IOException { 066 if (!isReadable()) { 067 throw new IllegalStateException("\'" + normalizedPathName + "\' is not readable"); 068 } 069 return Files.newInputStream(getPath()); 070 } 071 072 /** 073 * Checks and modifies a given pathName 074 * 075 * @param pathName must not be null nor empty, must not start with the prefix 076 * "classpath:" but may start with the prefix 077 * "file:" and contain at least one character despite the prefix. On all other cases 078 * a {@link IllegalArgumentException} will be 079 * thrown. 080 * 081 * @return the normalized pathname without prefix 082 */ 083 public static String checkPathName(final String pathName) { 084 MoreStrings.requireNotEmpty(pathName, "pathName"); 085 if (pathName.startsWith(FileTypePrefix.CLASSPATH.getPrefix())) { 086 throw new IllegalArgumentException("Invalid path name, must start not start with " + FileTypePrefix.CLASSPATH + " but was: " + pathName); 087 } 088 var newPathName = pathName; 089 if (pathName.startsWith(FileTypePrefix.FILE.getPrefix())) { 090 newPathName = FileTypePrefix.FILE.removePrefix(pathName); 091 } else if (pathName.startsWith(FileTypePrefix.EXTERNAL.getPrefix())) { 092 try { 093 newPathName = new java.io.File(".").getCanonicalPath() + FileTypePrefix.EXTERNAL.removePrefix(pathName); 094 LOG.debug("Loading config file from external path: {}", newPathName); 095 } catch (final IOException e) { 096 LOG.error("Retrieving the current dir failed: ", e); 097 } 098 } 099 if (isEmpty(newPathName)) { 100 throw new IllegalArgumentException("Filename " + pathName + " is invalid"); 101 } 102 return MorePaths.getRealPathSafely(newPathName).toString(); 103 } 104 105 @Override 106 public boolean isFilesystemLoader() { 107 return true; 108 } 109 110 @Override 111 public URL getURL() { 112 try { 113 return getPath().toUri().toURL(); 114 } catch (final MalformedURLException e) { 115 throw new IllegalStateException(e); 116 } 117 } 118 119 /** 120 * Truncate and overwrite an existing file, or create the file if it doesn't initially exist. 121 */ 122 @Override 123 public OutputStream outputStream() throws IOException { 124 if (!isWritable()) { 125 throw new IllegalStateException(normalizedPathName + " is not writable"); 126 } 127 return Files.newOutputStream(getPath()); 128 } 129 130 @java.lang.Override 131 @java.lang.SuppressWarnings("all") 132 @lombok.Generated 133 public boolean equals(final java.lang.Object o) { 134 if (o == this) return true; 135 if (!(o instanceof FileSystemLoader)) return false; 136 final FileSystemLoader other = (FileSystemLoader) o; 137 if (!other.canEqual((java.lang.Object) this)) return false; 138 final java.lang.Object this$normalizedPathName = this.normalizedPathName; 139 final java.lang.Object other$normalizedPathName = other.normalizedPathName; 140 if (this$normalizedPathName == null ? other$normalizedPathName != null : !this$normalizedPathName.equals(other$normalizedPathName)) return false; 141 return true; 142 } 143 144 @java.lang.SuppressWarnings("all") 145 @lombok.Generated 146 protected boolean canEqual(final java.lang.Object other) { 147 return other instanceof FileSystemLoader; 148 } 149 150 @java.lang.Override 151 @java.lang.SuppressWarnings("all") 152 @lombok.Generated 153 public int hashCode() { 154 final int PRIME = 59; 155 int result = 1; 156 final java.lang.Object $normalizedPathName = this.normalizedPathName; 157 result = result * PRIME + ($normalizedPathName == null ? 43 : $normalizedPathName.hashCode()); 158 return result; 159 } 160 161 @java.lang.Override 162 @java.lang.SuppressWarnings("all") 163 @lombok.Generated 164 public java.lang.String toString() { 165 return "FileSystemLoader(normalizedPathName=" + this.normalizedPathName + ", readable=" + this.isReadable() + ", writable=" + this.isWritable() + ", fileName=" + this.getFileName() + ")"; 166 } 167 168 @java.lang.SuppressWarnings("all") 169 @lombok.Generated 170 public boolean isReadable() { 171 return this.readable; 172 } 173 174 @java.lang.SuppressWarnings("all") 175 @lombok.Generated 176 public boolean isWritable() { 177 return this.writable; 178 } 179 180 @java.lang.SuppressWarnings("all") 181 @lombok.Generated 182 public StructuredFilename getFileName() { 183 return this.fileName; 184 } 185}