package automately.core.file.nio;
import automately.core.Automately;
import automately.core.data.User;
import io.jsync.app.core.Cluster;
import io.jsync.app.core.Logger;
import java.io.IOException;
import java.net.URI;
import java.nio.channels.FileChannel;
import java.nio.channels.SeekableByteChannel;
import java.nio.file.*;
import java.nio.file.attribute.BasicFileAttributes;
import java.nio.file.attribute.FileAttribute;
import java.nio.file.attribute.FileAttributeView;
import java.nio.file.spi.FileSystemProvider;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
public class UserFileSystemProvider extends FileSystemProvider {
private final static Map<String, UserFileSystemProvider> providers = new ConcurrentHashMap<>();
public static UserFileSystemProvider create(User user){
UserFileSystemProvider provider = providers.get(user.token());
if(provider == null){
provider = new UserFileSystemProvider(user, Automately.activeInstance().cluster());
providers.put(user.token(), provider);
}
return provider;
}
private final Logger logger;
private UserFileSystem fileSystem = null;
private Cluster cluster = null;
private User user = null;
UserFileSystemProvider(User user, Cluster cluster){
super();
this.user = user;
this.cluster = cluster;
this.logger = cluster.logger();
logger.debug("Creating new UserFileSystemProvider for the user " + user.username);
}
@Override
public String getScheme() {
return "uservfs";
}
@Override
public UserFileSystem newFileSystem(URI uri, Map<String, ?> env) throws IOException {
if (fileSystem != null) {
throw new FileSystemAlreadyExistsException(uri.getSchemeSpecificPart());
}
fileSystem = new UserFileSystem(this, user, cluster);
return fileSystem;
}
@Override
public UserFileSystem newFileSystem(Path path, Map<String, ?> env) throws IOException {
String pathS = path.toString();
if (fileSystem != null) {
throw new FileSystemAlreadyExistsException(pathS);
}
fileSystem = new UserFileSystem(this, user, cluster);
return fileSystem;
}
@Override
public UserFileSystem getFileSystem(URI uri) {
String schemeSpecificPart = uri.getSchemeSpecificPart();
if (fileSystem == null) {
try {
fileSystem = newFileSystem(uri, null);
} catch (IOException e) {
throw (FileSystemNotFoundException) new FileSystemNotFoundException(schemeSpecificPart).initCause(e);
}
}
return fileSystem;
}
@Override
public Path getPath(URI uri) {
String str = uri.getSchemeSpecificPart();
return getFileSystem(uri).getPath(str);
}
@Override
public FileChannel newFileChannel(Path path, Set<? extends OpenOption> options,
FileAttribute<?>... attrs) throws IOException {
if (!(path instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
return ((UserFilePath) path).getFileSystem().newFileChannel(path, options, attrs);
}
@Override
public SeekableByteChannel newByteChannel(Path path, Set<? extends OpenOption> options, FileAttribute<?>... attrs) throws IOException {
if (!(path instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
return ((UserFilePath) path).getFileSystem().newByteChannel(path, options, attrs);
}
@Override
public DirectoryStream<Path> newDirectoryStream(Path dir, DirectoryStream.Filter<? super Path> filter) throws IOException {
if (!(dir instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
return ((UserFilePath) dir).getFileSystem().newDirectoryStream(dir, filter);
}
@Override
public void createDirectory(Path dir, FileAttribute<?>... attrs) throws IOException {
if (!(dir instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
((UserFilePath) dir).getFileSystem().createDirectory(dir, attrs);
}
@Override
public void delete(Path path) throws IOException {
if (!(path instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
((UserFilePath) path).getFileSystem().delete(path);
}
@Override
public void copy(Path source, Path target, CopyOption... options) throws IOException {
if (!(source instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
if (!(target instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
// Is copy same as move???
((UserFilePath) source).getFileSystem().copy(source, target, options);
}
@Override
public void move(Path source, Path target, CopyOption... options) throws IOException {
if (!(source instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
if (!(target instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
((UserFilePath) source).getFileSystem().move(source, target, options);
}
@Override
public boolean isSameFile(Path path, Path path2) throws IOException {
if (!(path instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
if (!(path2 instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
return path.toAbsolutePath().toString().equals(path2.toAbsolutePath().toString());
}
@Override
public boolean isHidden(Path path) throws IOException {
if (!(path instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
return false;
}
@Override
public FileStore getFileStore(Path path) throws IOException {
throw new UnsupportedOperationException();
}
@Override
public void checkAccess(Path path, AccessMode... modes) throws IOException {
if (!(path instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
((UserFilePath) path).getFileSystem().checkAccess(path, modes);
}
@Override
public <V extends FileAttributeView> V getFileAttributeView(Path path, Class<V> type, LinkOption... options) {
throw new UnsupportedOperationException();
}
@Override
public <A extends BasicFileAttributes> A readAttributes(Path path, Class<A> type, LinkOption... options) throws IOException {
if (!(path instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
return ((UserFilePath) path).getFileSystem().readAttributes(path, type, options);
}
@Override
public Map<String, Object> readAttributes(Path path, String attributes, LinkOption... options) throws IOException {
if (!(path instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
return ((UserFilePath) path).getFileSystem().readAttributes(path, attributes, options);
}
@Override
public void setAttribute(Path path, String attribute, Object value, LinkOption... options) throws IOException {
if (!(path instanceof UserFilePath)) {
throw new ProviderMismatchException();
}
((UserFilePath) path).getFileSystem().setAttribute(path, attribute, value, options);
}
}