Skip to content

Commit

Permalink
Merge branch 'release/1.1.0'
Browse files Browse the repository at this point in the history
# Conflicts:
#	pom.xml
#	src/test/java/org/cryptomator/cryptofs/CryptoFileChannelTest.java
  • Loading branch information
overheadhunter committed Feb 24, 2017
2 parents 373a02f + af638ce commit 17c2413
Show file tree
Hide file tree
Showing 61 changed files with 3,674 additions and 297 deletions.
1 change: 0 additions & 1 deletion .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,6 @@ deploy:
- "target/dependency-list.txt"
- "target/*.jar"
skip_cleanup: true
prerelease: true
on:
repo: cryptomator/cryptofs
tags: true
7 changes: 4 additions & 3 deletions pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
<modelVersion>4.0.0</modelVersion>
<groupId>org.cryptomator</groupId>
<artifactId>cryptofs</artifactId>
<version>1.0.1</version>
<version>1.1.0</version>
<name>Cryptomator Crypto Filesystem</name>
<description>This library provides the Java filesystem provider used by Cryptomator.</description>
<url>https://github.com/cryptomator/cryptofs</url>
Expand All @@ -15,6 +15,7 @@

<properties>
<java.version>1.8</java.version>
<cryptolib.version>1.1.0</cryptolib.version>
<dagger.version>2.8</dagger.version>
<guava.version>21.0</guava.version>
<commons.lang.version>3.5</commons.lang.version>
Expand Down Expand Up @@ -64,7 +65,7 @@
<dependency>
<groupId>org.cryptomator</groupId>
<artifactId>cryptolib</artifactId>
<version>1.0.10</version>
<version>${cryptolib.version}</version>
</dependency>
<dependency>
<groupId>org.apache.commons</groupId>
Expand Down Expand Up @@ -280,7 +281,7 @@
</plugin>
<plugin>
<artifactId>maven-dependency-plugin</artifactId>
<version>2.10</version>
<version>3.0.0</version>
<executions>
<execution>
<id>generate-dependency-list</id>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@
package org.cryptomator.cryptofs;

import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.attribute.BasicFileAttributeView;
import java.nio.file.attribute.BasicFileAttributes;
Expand All @@ -26,7 +25,7 @@ public AbstractCryptoFileAttributeView(Path ciphertextPath, CryptoFileAttributeP
this.ciphertextPath = ciphertextPath;
this.fileAttributeProvider = fileAttributeProvider;
this.attributesType = attributesType;
this.delegate = Files.getFileAttributeView(ciphertextPath, delegateType);
this.delegate = ciphertextPath.getFileSystem().provider().getFileAttributeView(ciphertextPath, delegateType);
if (delegate == null) {
throw new UnsupportedFileAttributeViewException();
}
Expand Down
3 changes: 1 addition & 2 deletions src/main/java/org/cryptomator/cryptofs/Constants.java
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,7 @@

final class Constants {

public static final String MASTERKEY_FILE_NAME = "masterkey.cryptomator";
public static final String BACKUPKEY_FILE_NAME = "masterkey.cryptomator.bkup";
public static final String MASTERKEY_BACKUP_SUFFIX = ".bkup";
public static final String DATA_DIR_NAME = "d";
public static final String METADATA_DIR_NAME = "m";
public static final String DIR_PREFIX = "0";
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
package org.cryptomator.cryptofs;

import static java.nio.file.StandardCopyOption.ATOMIC_MOVE;
import static java.nio.file.StandardCopyOption.COPY_ATTRIBUTES;
import static java.nio.file.StandardCopyOption.REPLACE_EXISTING;
import static java.nio.file.StandardOpenOption.CREATE_NEW;
Expand All @@ -9,12 +8,9 @@

import java.io.IOException;
import java.nio.channels.FileChannel;
import java.nio.file.AtomicMoveNotSupportedException;
import java.nio.file.CopyOption;
import java.nio.file.DirectoryStream;
import java.nio.file.FileAlreadyExistsException;
import java.nio.file.NoSuchFileException;
import java.nio.file.Path;
import java.nio.file.attribute.BasicFileAttributeView;
import java.nio.file.attribute.BasicFileAttributes;
import java.nio.file.spi.FileSystemProvider;
Expand All @@ -26,10 +22,10 @@
import org.apache.commons.lang3.ArrayUtils;

@PerProvider
class CopyAndMoveOperations {
class CopyOperation {

@Inject
public CopyAndMoveOperations() {
public CopyOperation() {
}

public void copy(CryptoPath source, CryptoPath target, CopyOption... options) throws IOException {
Expand Down Expand Up @@ -81,51 +77,10 @@ private FileSystemProvider provider(CryptoPath path) {
return path.getFileSystem().provider();
}

public void move(CryptoPath source, CryptoPath target, CopyOption... options) throws IOException {
if (source.equals(target)) {
return;
}
if (pathsBelongToSameFileSystem(source, target)) {
source.getFileSystem().move(source, target, options);
} else {
if (ArrayUtils.contains(options, ATOMIC_MOVE)) {
throw new AtomicMoveNotSupportedException(source.toUri().toString(), target.toUri().toString(), "Move of encrypted file to different FileSystem");
}
if (isNonEmptyDirectory(source)) {
throw new IOException("Can not move non empty directory to different FileSystem");
}
boolean success = false;
try {
copy(source, target, addCopyAttributesTo(options));
success = true;
} finally {
if (!success) {
// do a best effort to clean a partially copied file
try {
provider(target).deleteIfExists(target);
} catch (IOException e) {
// ignore
}
}
}
provider(source).deleteIfExists(source);
}
}

private boolean pathsBelongToSameFileSystem(CryptoPath source, CryptoPath target) {
return source.getFileSystem() == target.getFileSystem();
}

private boolean isNonEmptyDirectory(CryptoPath source) throws IOException {
Optional<BasicFileAttributes> sourceAttrs = attributes(source);
if (!sourceAttrs.map(BasicFileAttributes::isDirectory).orElse(false)) {
return false;
}
try (DirectoryStream<Path> contents = provider(source).newDirectoryStream(source, ignored -> true)) {
return contents.iterator().hasNext();
}
}

private Optional<BasicFileAttributes> attributes(CryptoPath path) {
try {
return Optional.of(provider(path).readAttributes(path, BasicFileAttributes.class));
Expand All @@ -134,13 +89,4 @@ private Optional<BasicFileAttributes> attributes(CryptoPath path) {
}
}

private CopyOption[] addCopyAttributesTo(CopyOption[] options) {
CopyOption[] result = new CopyOption[options.length + 1];
for (int i = 0; i < options.length; i++) {
result[i] = options[i];
}
result[options.length] = COPY_ATTRIBUTES;
return result;
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,6 @@
*******************************************************************************/
package org.cryptomator.cryptofs;

import static org.cryptomator.cryptofs.FinallyUtils.guaranteeInvocationOf;

import java.io.IOException;
import java.io.UncheckedIOException;
import java.nio.charset.StandardCharsets;
Expand Down Expand Up @@ -42,10 +40,12 @@ class CryptoDirectoryStream implements DirectoryStream<Path> {
private final LongFileNameProvider longFileNameProvider;
private final DirectoryStream.Filter<? super Path> filter;
private final Consumer<CryptoDirectoryStream> onClose;
private final FinallyUtil finallyUtil;

public CryptoDirectoryStream(Directory ciphertextDir, Path cleartextDir, FileNameCryptor filenameCryptor, LongFileNameProvider longFileNameProvider, DirectoryStream.Filter<? super Path> filter,
Consumer<CryptoDirectoryStream> onClose) throws IOException {
Consumer<CryptoDirectoryStream> onClose, FinallyUtil finallyUtil) throws IOException {
this.onClose = onClose;
this.finallyUtil = finallyUtil;
this.directoryId = ciphertextDir.dirId;
this.ciphertextDirStream = Files.newDirectoryStream(ciphertextDir.path, p -> true);
LOG.trace("OPEN " + directoryId);
Expand Down Expand Up @@ -106,8 +106,9 @@ private boolean isAcceptableByFilter(Path path) {
}

@Override
@SuppressWarnings("unchecked")
public void close() throws IOException {
guaranteeInvocationOf( //
finallyUtil.guaranteeInvocationOf( //
() -> ciphertextDirStream.close(), //
() -> onClose.accept(this), //
() -> LOG.trace("CLOSE " + directoryId));
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@
class CryptoFileAttributeByNameProvider {

private static final SortedMap<String, AttributeGetter<?>> GETTERS = new TreeMap<>();
{
static {
attribute("basic:lastModifiedTime", BasicFileAttributes.class, BasicFileAttributes::lastModifiedTime);
attribute("basic:lastAccessTime", BasicFileAttributes.class, BasicFileAttributes::lastAccessTime);
attribute("basic:creationTime", BasicFileAttributes.class, BasicFileAttributes::creationTime);
Expand All @@ -63,7 +63,7 @@ class CryptoFileAttributeByNameProvider {
}

private static final SortedMap<String, AttributeSetter<?, ?>> SETTERS = new TreeMap<>();
{
static {
attribute("basic:lastModifiedTime", BasicFileAttributeView.class, FileTime.class, (view, lastModifiedTime) -> view.setTimes(lastModifiedTime, null, null));
attribute("basic:lastAccessTime", BasicFileAttributeView.class, FileTime.class, (view, lastAccessTime) -> view.setTimes(null, lastAccessTime, null));
attribute("basic:creationTime", BasicFileAttributeView.class, FileTime.class, (view, creationTime) -> view.setTimes(null, null, creationTime));
Expand All @@ -78,12 +78,12 @@ class CryptoFileAttributeByNameProvider {
attribute("posix:permissions", PosixFileAttributeView.class, Set.class, PosixFileAttributeView::setPermissions);
}

private <T extends BasicFileAttributes> void attribute(String name, Class<T> type, Function<T, ?> getter) {
private static <T extends BasicFileAttributes> void attribute(String name, Class<T> type, Function<T, ?> getter) {
String plainName = name.substring(name.indexOf(':') + 1);
GETTERS.put(name, new AttributeGetter<>(plainName, type, getter));
}

private <T extends BasicFileAttributeView, V> void attribute(String name, Class<T> type, Class<V> valueType, BiConsumerThrowingException<T, V, IOException> setter) {
private static <T extends BasicFileAttributeView, V> void attribute(String name, Class<T> type, Class<V> valueType, BiConsumerThrowingException<T, V, IOException> setter) {
SETTERS.put(name, new AttributeSetter<>(type, valueType, setter));
}

Expand Down Expand Up @@ -125,7 +125,7 @@ private Map<String, Object> readAttributes(Path path, Collection<AttributeGetter
Map<String, Object> result = new HashMap<>();
BasicFileAttributes attributes = null;
for (AttributeGetter getter : getters) {
if (!getter.type().isInstance(attributes)) {
if (attributes == null) {
attributes = cryptoFileAttributeProvider.readAttributes(path, getter.type());
}
String name = getter.name();
Expand Down
8 changes: 5 additions & 3 deletions src/main/java/org/cryptomator/cryptofs/CryptoFileChannel.java
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@
package org.cryptomator.cryptofs;

import static java.lang.Math.min;
import static org.cryptomator.cryptofs.FinallyUtils.guaranteeInvocationOf;

import java.io.IOException;
import java.nio.ByteBuffer;
Expand All @@ -29,18 +28,20 @@ class CryptoFileChannel extends FileChannel {
private final OpenCryptoFile openCryptoFile;
private final EffectiveOpenOptions options;
private final Consumer<CryptoFileChannel> onClose;
private final FinallyUtil finallyUtil;

private volatile long position = 0;

/**
* @throws IOException
* @throws ClosedChannelException if the openCryptoFile has already been closed
*/
public CryptoFileChannel(OpenCryptoFile openCryptoFile, EffectiveOpenOptions options, Consumer<CryptoFileChannel> onClose) throws IOException {
public CryptoFileChannel(OpenCryptoFile openCryptoFile, EffectiveOpenOptions options, Consumer<CryptoFileChannel> onClose, FinallyUtil finallyUtil) throws IOException {
this.openCryptoFile = Objects.requireNonNull(openCryptoFile);
this.options = Objects.requireNonNull(options);
this.openCryptoFile.open(options);
this.onClose = onClose;
this.finallyUtil = finallyUtil;
}

@Override
Expand Down Expand Up @@ -253,9 +254,10 @@ public FileLock tryLock(long position, long size, boolean shared) throws IOExcep

}

@SuppressWarnings("unchecked")
@Override
protected void implCloseChannel() throws IOException {
guaranteeInvocationOf( //
finallyUtil.guaranteeInvocationOf( //
() -> onClose.accept(this), //
() -> openCryptoFile.close(options));
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,5 @@
package org.cryptomator.cryptofs;

import static org.cryptomator.cryptofs.FinallyUtils.guaranteeInvocationOf;

import java.io.IOException;
import java.nio.file.ClosedFileSystemException;
import java.util.concurrent.ConcurrentHashMap;
Expand All @@ -14,24 +12,30 @@ class CryptoFileChannelFactory {

private final ConcurrentMap<CryptoFileChannel, CryptoFileChannel> channels = new ConcurrentHashMap<>();
private volatile boolean closed = false;
private final FinallyUtil finallyUtil;

@Inject
public CryptoFileChannelFactory() {
public CryptoFileChannelFactory(FinallyUtil finallyUtil) {
this.finallyUtil = finallyUtil;
}

@SuppressWarnings("finally")
public CryptoFileChannel create(OpenCryptoFile openCryptoFile, EffectiveOpenOptions options) throws IOException {
CryptoFileChannel channel = new CryptoFileChannel(openCryptoFile, options, closed -> channels.remove(closed));
CryptoFileChannel channel = new CryptoFileChannel(openCryptoFile, options, closed -> channels.remove(closed), finallyUtil);
channels.put(channel, channel);
if (closed) {
channel.close();
throw new ClosedFileSystemException();
try {
channel.close();
} finally {
throw new ClosedFileSystemException();
}
}
return channel;
}

public void close() throws IOException {
closed = true;
guaranteeInvocationOf( //
finallyUtil.guaranteeInvocationOf( //
channels.keySet().stream() //
.map(channel -> (RunnableThrowingException<IOException>) () -> channel.close()) //
.iterator());
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
import dagger.Subcomponent;

@PerFileSystem
@Subcomponent(modules = {CryptoFileSystemModule.class, CryptoFileSystemFactoryModule.class})
@Subcomponent(modules = {CryptoFileSystemModule.class})
interface CryptoFileSystemComponent {

CryptoFileSystemImpl cryptoFileSystem();
Expand Down

This file was deleted.

Loading

0 comments on commit 17c2413

Please sign in to comment.