From 8f4a0ef030bef6e43ebed652e5dc11bf5037bf90 Mon Sep 17 00:00:00 2001 From: akwizgran Date: Fri, 7 May 2021 12:15:51 +0100 Subject: [PATCH 1/9] Add removable drive manager with placeholder task implementations. --- .../file/AndroidRemovableDrivePlugin.java | 2 +- .../AndroidRemovableDrivePluginFactory.java | 2 +- .../briarproject/bramble/api/Consumer.java | 9 ++ .../api/plugin/{ => file}/FileConstants.java | 2 +- .../{ => file}/RemovableDriveConstants.java | 4 +- .../plugin/file/RemovableDriveManager.java | 40 +++++++++ .../api/plugin/file/RemovableDriveTask.java | 34 ++++++++ .../file/AbstractRemovableDrivePlugin.java | 2 +- .../bramble/plugin/file/FilePlugin.java | 2 +- .../file/RemovableDriveManagerImpl.java | 83 +++++++++++++++++++ .../plugin/file/RemovableDriveModule.java | 19 +++++ .../plugin/file/RemovableDrivePlugin.java | 2 +- .../file/RemovableDrivePluginFactory.java | 2 +- .../plugin/file/RemovableDriveTaskImpl.java | 54 ++++++++++++ .../file/RemovableDriveTaskRegistry.java | 13 +++ .../file/RemovableDriverReaderTask.java | 46 ++++++++++ .../file/RemovableDriverWriterTask.java | 46 ++++++++++ .../briar/android/AndroidComponent.java | 4 +- 18 files changed, 357 insertions(+), 9 deletions(-) create mode 100644 bramble-api/src/main/java/org/briarproject/bramble/api/Consumer.java rename bramble-api/src/main/java/org/briarproject/bramble/api/plugin/{ => file}/FileConstants.java (56%) rename bramble-api/src/main/java/org/briarproject/bramble/api/plugin/{ => file}/RemovableDriveConstants.java (61%) create mode 100644 bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveManager.java create mode 100644 bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java create mode 100644 bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveManagerImpl.java create mode 100644 bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveModule.java create mode 100644 bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java create mode 100644 bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskRegistry.java create mode 100644 bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverReaderTask.java create mode 100644 bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverWriterTask.java diff --git a/bramble-android/src/main/java/org/briarproject/bramble/plugin/file/AndroidRemovableDrivePlugin.java b/bramble-android/src/main/java/org/briarproject/bramble/plugin/file/AndroidRemovableDrivePlugin.java index bee061db1..05e569f7c 100644 --- a/bramble-android/src/main/java/org/briarproject/bramble/plugin/file/AndroidRemovableDrivePlugin.java +++ b/bramble-android/src/main/java/org/briarproject/bramble/plugin/file/AndroidRemovableDrivePlugin.java @@ -12,7 +12,7 @@ import java.io.OutputStream; import javax.annotation.concurrent.Immutable; -import static org.briarproject.bramble.api.plugin.RemovableDriveConstants.PROP_URI; +import static org.briarproject.bramble.api.plugin.file.RemovableDriveConstants.PROP_URI; import static org.briarproject.bramble.util.StringUtils.isNullOrEmpty; @Immutable diff --git a/bramble-android/src/main/java/org/briarproject/bramble/plugin/file/AndroidRemovableDrivePluginFactory.java b/bramble-android/src/main/java/org/briarproject/bramble/plugin/file/AndroidRemovableDrivePluginFactory.java index 68d32d924..64f6cf534 100644 --- a/bramble-android/src/main/java/org/briarproject/bramble/plugin/file/AndroidRemovableDrivePluginFactory.java +++ b/bramble-android/src/main/java/org/briarproject/bramble/plugin/file/AndroidRemovableDrivePluginFactory.java @@ -13,7 +13,7 @@ import javax.annotation.concurrent.Immutable; import javax.inject.Inject; import static java.util.concurrent.TimeUnit.DAYS; -import static org.briarproject.bramble.api.plugin.RemovableDriveConstants.ID; +import static org.briarproject.bramble.api.plugin.file.RemovableDriveConstants.ID; @Immutable @NotNullByDefault diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/Consumer.java b/bramble-api/src/main/java/org/briarproject/bramble/api/Consumer.java new file mode 100644 index 000000000..4e025a728 --- /dev/null +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/Consumer.java @@ -0,0 +1,9 @@ +package org.briarproject.bramble.api; + +import org.briarproject.bramble.api.nullsafety.NotNullByDefault; + +@NotNullByDefault +public interface Consumer { + + void accept(T t); +} diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/FileConstants.java b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/FileConstants.java similarity index 56% rename from bramble-api/src/main/java/org/briarproject/bramble/api/plugin/FileConstants.java rename to bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/FileConstants.java index bed296874..1564f415d 100644 --- a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/FileConstants.java +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/FileConstants.java @@ -1,4 +1,4 @@ -package org.briarproject.bramble.api.plugin; +package org.briarproject.bramble.api.plugin.file; public interface FileConstants { diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/RemovableDriveConstants.java b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveConstants.java similarity index 61% rename from bramble-api/src/main/java/org/briarproject/bramble/api/plugin/RemovableDriveConstants.java rename to bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveConstants.java index 98caf96c3..927e197df 100644 --- a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/RemovableDriveConstants.java +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveConstants.java @@ -1,4 +1,6 @@ -package org.briarproject.bramble.api.plugin; +package org.briarproject.bramble.api.plugin.file; + +import org.briarproject.bramble.api.plugin.TransportId; public interface RemovableDriveConstants { diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveManager.java b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveManager.java new file mode 100644 index 000000000..241582dab --- /dev/null +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveManager.java @@ -0,0 +1,40 @@ +package org.briarproject.bramble.api.plugin.file; + +import org.briarproject.bramble.api.contact.ContactId; +import org.briarproject.bramble.api.nullsafety.NotNullByDefault; + +import java.io.File; + +import javax.annotation.Nullable; + +@NotNullByDefault +public interface RemovableDriveManager { + + /** + * Returns the currently running reader task for the given contact, + * or null if no task is running. + */ + @Nullable + RemovableDriveTask getCurrentReaderTask(ContactId c); + + /** + * Returns the currently running writer task for the given contact, + * or null if no task is running. + */ + @Nullable + RemovableDriveTask getCurrentWriterTask(ContactId c); + + /** + * Starts and returns a reader task for the given contact, reading from + * the given file. If a reader task for the contact is already running, + * it will be returned and the file argument will be ignored. + */ + RemovableDriveTask startReaderTask(ContactId c, File f); + + /** + * Starts and returns a writer task for the given contact, writing to + * the given file. If a writer task for the contact is already running, + * it will be returned and the file argument will be ignored. + */ + RemovableDriveTask startWriterTask(ContactId c, File f); +} diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java new file mode 100644 index 000000000..08165c267 --- /dev/null +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java @@ -0,0 +1,34 @@ +package org.briarproject.bramble.api.plugin.file; + +import org.briarproject.bramble.api.event.EventExecutor; +import org.briarproject.bramble.api.nullsafety.NotNullByDefault; + +import java.io.File; + +@NotNullByDefault +public interface RemovableDriveTask { + + /** + * Returns the file that this task is reading from or writing to. + */ + File getFile(); + + /** + * Adds an observer to the task. + */ + void addObserver(Observer o); + + /** + * Removes an observer from the task. + */ + void removeObserver(Observer o); + + interface Observer { + + @EventExecutor + void onProgress(long written, long total); + + @EventExecutor + void onCompletion(boolean success); + } +} diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/AbstractRemovableDrivePlugin.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/AbstractRemovableDrivePlugin.java index 3fdc9c908..356186355 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/AbstractRemovableDrivePlugin.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/AbstractRemovableDrivePlugin.java @@ -20,7 +20,7 @@ import javax.annotation.concurrent.Immutable; import static java.util.logging.Level.WARNING; import static java.util.logging.Logger.getLogger; import static org.briarproject.bramble.api.plugin.Plugin.State.ACTIVE; -import static org.briarproject.bramble.api.plugin.RemovableDriveConstants.ID; +import static org.briarproject.bramble.api.plugin.file.RemovableDriveConstants.ID; import static org.briarproject.bramble.util.LogUtils.logException; @Immutable diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/FilePlugin.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/FilePlugin.java index 8a2673a7a..34ca014f2 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/FilePlugin.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/FilePlugin.java @@ -15,8 +15,8 @@ import java.util.logging.Logger; import static java.util.logging.Level.WARNING; import static java.util.logging.Logger.getLogger; -import static org.briarproject.bramble.api.plugin.FileConstants.PROP_PATH; import static org.briarproject.bramble.api.plugin.Plugin.State.ACTIVE; +import static org.briarproject.bramble.api.plugin.file.FileConstants.PROP_PATH; import static org.briarproject.bramble.util.LogUtils.logException; import static org.briarproject.bramble.util.StringUtils.isNullOrEmpty; diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveManagerImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveManagerImpl.java new file mode 100644 index 000000000..4b6d9dffc --- /dev/null +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveManagerImpl.java @@ -0,0 +1,83 @@ +package org.briarproject.bramble.plugin.file; + +import org.briarproject.bramble.api.contact.ContactId; +import org.briarproject.bramble.api.event.EventExecutor; +import org.briarproject.bramble.api.lifecycle.IoExecutor; +import org.briarproject.bramble.api.nullsafety.NotNullByDefault; +import org.briarproject.bramble.api.plugin.file.RemovableDriveManager; +import org.briarproject.bramble.api.plugin.file.RemovableDriveTask; + +import java.io.File; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.Executor; + +import javax.annotation.Nullable; +import javax.annotation.concurrent.ThreadSafe; +import javax.inject.Inject; + +@ThreadSafe +@NotNullByDefault +class RemovableDriveManagerImpl + implements RemovableDriveManager, RemovableDriveTaskRegistry { + + private final Executor ioExecutor, eventExecutor; + private final ConcurrentHashMap + readers = new ConcurrentHashMap<>(); + private final ConcurrentHashMap + writers = new ConcurrentHashMap<>(); + + @Inject + RemovableDriveManagerImpl(@IoExecutor Executor ioExecutor, + @EventExecutor Executor eventExecutor) { + this.ioExecutor = ioExecutor; + this.eventExecutor = eventExecutor; + } + + @Nullable + @Override + public RemovableDriveTask getCurrentReaderTask(ContactId c) { + return readers.get(c); + } + + @Nullable + @Override + public RemovableDriveTask getCurrentWriterTask(ContactId c) { + return writers.get(c); + } + + @Override + public RemovableDriveTask startReaderTask(ContactId c, File f) { + RemovableDriverReaderTask task = + new RemovableDriverReaderTask(eventExecutor, this, c, f); + RemovableDriveTask old = readers.putIfAbsent(c, task); + if (old == null) { + ioExecutor.execute(task); + return task; + } else { + return old; + } + } + + @Override + public RemovableDriveTask startWriterTask(ContactId c, File f) { + RemovableDriverWriterTask task = + new RemovableDriverWriterTask(eventExecutor, this, c, f); + RemovableDriveTask old = writers.putIfAbsent(c, task); + if (old == null) { + ioExecutor.execute(task); + return task; + } else { + return old; + } + } + + @Override + public void removeReader(ContactId c, RemovableDriveTask task) { + readers.remove(c, task); + } + + @Override + public void removeWriter(ContactId c, RemovableDriveTask task) { + writers.remove(c, task); + } +} diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveModule.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveModule.java new file mode 100644 index 000000000..92455bb3a --- /dev/null +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveModule.java @@ -0,0 +1,19 @@ +package org.briarproject.bramble.plugin.file; + +import org.briarproject.bramble.api.plugin.file.RemovableDriveManager; + +import javax.inject.Singleton; + +import dagger.Module; +import dagger.Provides; + +@Module +public class RemovableDriveModule { + + @Provides + @Singleton + RemovableDriveManager provideRemovableDriveManager( + RemovableDriveManagerImpl removableDriveManager) { + return removableDriveManager; + } +} diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDrivePlugin.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDrivePlugin.java index 9904ff834..cb6653134 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDrivePlugin.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDrivePlugin.java @@ -11,7 +11,7 @@ import java.io.OutputStream; import javax.annotation.concurrent.Immutable; -import static org.briarproject.bramble.api.plugin.RemovableDriveConstants.PROP_PATH; +import static org.briarproject.bramble.api.plugin.file.RemovableDriveConstants.PROP_PATH; import static org.briarproject.bramble.util.StringUtils.isNullOrEmpty; @Immutable diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDrivePluginFactory.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDrivePluginFactory.java index e43a89d93..6f1ad7564 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDrivePluginFactory.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDrivePluginFactory.java @@ -11,7 +11,7 @@ import javax.annotation.concurrent.Immutable; import javax.inject.Inject; import static java.util.concurrent.TimeUnit.DAYS; -import static org.briarproject.bramble.api.plugin.RemovableDriveConstants.ID; +import static org.briarproject.bramble.api.plugin.file.RemovableDriveConstants.ID; @Immutable @NotNullByDefault diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java new file mode 100644 index 000000000..0af720b77 --- /dev/null +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java @@ -0,0 +1,54 @@ +package org.briarproject.bramble.plugin.file; + +import org.briarproject.bramble.api.Consumer; +import org.briarproject.bramble.api.contact.ContactId; +import org.briarproject.bramble.api.nullsafety.NotNullByDefault; +import org.briarproject.bramble.api.plugin.file.RemovableDriveTask; + +import java.io.File; +import java.util.List; +import java.util.concurrent.CopyOnWriteArrayList; +import java.util.concurrent.Executor; + +import javax.annotation.concurrent.ThreadSafe; + +@ThreadSafe +@NotNullByDefault +abstract class RemovableDriveTaskImpl implements RemovableDriveTask, Runnable { + + private final Executor eventExecutor; + final RemovableDriveTaskRegistry registry; + final ContactId contactId; + final File file; + private final List observers = new CopyOnWriteArrayList<>(); + + RemovableDriveTaskImpl(Executor eventExecutor, + RemovableDriveTaskRegistry registry, ContactId contactId, + File file) { + this.contactId = contactId; + this.file = file; + this.registry = registry; + this.eventExecutor = eventExecutor; + } + + @Override + public File getFile() { + return file; + } + + @Override + public void addObserver(Observer o) { + observers.add(o); + } + + @Override + public void removeObserver(Observer o) { + observers.remove(o); + } + + void visitObservers(Consumer visitor) { + eventExecutor.execute(() -> { + for (Observer o : observers) visitor.accept(o); + }); + } +} diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskRegistry.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskRegistry.java new file mode 100644 index 000000000..84ee40092 --- /dev/null +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskRegistry.java @@ -0,0 +1,13 @@ +package org.briarproject.bramble.plugin.file; + +import org.briarproject.bramble.api.contact.ContactId; +import org.briarproject.bramble.api.nullsafety.NotNullByDefault; +import org.briarproject.bramble.api.plugin.file.RemovableDriveTask; + +@NotNullByDefault +interface RemovableDriveTaskRegistry { + + void removeReader(ContactId c, RemovableDriveTask task); + + void removeWriter(ContactId c, RemovableDriveTask task); +} diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverReaderTask.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverReaderTask.java new file mode 100644 index 000000000..3cc53c7b4 --- /dev/null +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverReaderTask.java @@ -0,0 +1,46 @@ +package org.briarproject.bramble.plugin.file; + +import org.briarproject.bramble.api.contact.ContactId; +import org.briarproject.bramble.api.nullsafety.NotNullByDefault; + +import java.io.File; +import java.io.FileInputStream; +import java.io.IOException; +import java.io.InputStream; +import java.util.concurrent.Executor; +import java.util.logging.Logger; + +import static java.util.logging.Level.WARNING; +import static java.util.logging.Logger.getLogger; +import static org.briarproject.bramble.util.IoUtils.tryToClose; +import static org.briarproject.bramble.util.LogUtils.logException; + +@NotNullByDefault +class RemovableDriverReaderTask extends RemovableDriveTaskImpl { + + private final static Logger LOG = + getLogger(RemovableDriverReaderTask.class.getName()); + + RemovableDriverReaderTask(Executor eventExecutor, + RemovableDriveTaskRegistry registry, ContactId contactId, + File file) { + super(eventExecutor, registry, contactId, file); + } + + @Override + public void run() { + // TODO + InputStream in = null; + try { + visitObservers(o -> o.onProgress(0, 100)); + in = new FileInputStream(file); + visitObservers(o -> o.onCompletion(true)); + } catch (IOException e) { + logException(LOG, WARNING, e); + visitObservers(o -> o.onCompletion(false)); + } finally { + tryToClose(in, LOG, WARNING); + registry.removeReader(contactId, this); + } + } +} diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverWriterTask.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverWriterTask.java new file mode 100644 index 000000000..ed0715d16 --- /dev/null +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverWriterTask.java @@ -0,0 +1,46 @@ +package org.briarproject.bramble.plugin.file; + +import org.briarproject.bramble.api.contact.ContactId; +import org.briarproject.bramble.api.nullsafety.NotNullByDefault; + +import java.io.File; +import java.io.FileOutputStream; +import java.io.IOException; +import java.io.OutputStream; +import java.util.concurrent.Executor; +import java.util.logging.Logger; + +import static java.util.logging.Level.WARNING; +import static java.util.logging.Logger.getLogger; +import static org.briarproject.bramble.util.IoUtils.tryToClose; +import static org.briarproject.bramble.util.LogUtils.logException; + +@NotNullByDefault +class RemovableDriverWriterTask extends RemovableDriveTaskImpl { + + private static final Logger LOG = + getLogger(RemovableDriverWriterTask.class.getName()); + + RemovableDriverWriterTask(Executor eventExecutor, + RemovableDriveTaskRegistry registry, ContactId contactId, + File file) { + super(eventExecutor, registry, contactId, file); + } + + @Override + public void run() { + // TODO + OutputStream out = null; + try { + visitObservers(o -> o.onProgress(0, 100)); + out = new FileOutputStream(file); + visitObservers(o -> o.onCompletion(true)); + } catch (IOException e) { + logException(LOG, WARNING, e); + visitObservers(o -> o.onCompletion(false)); + } finally { + tryToClose(out, LOG, WARNING); + registry.removeWriter(contactId, this); + } + } +} diff --git a/briar-android/src/main/java/org/briarproject/briar/android/AndroidComponent.java b/briar-android/src/main/java/org/briarproject/briar/android/AndroidComponent.java index aeed5817f..f2b3d6197 100644 --- a/briar-android/src/main/java/org/briarproject/briar/android/AndroidComponent.java +++ b/briar-android/src/main/java/org/briarproject/briar/android/AndroidComponent.java @@ -28,6 +28,7 @@ import org.briarproject.bramble.api.system.AndroidExecutor; import org.briarproject.bramble.api.system.AndroidWakeLockManager; import org.briarproject.bramble.api.system.Clock; import org.briarproject.bramble.api.system.LocationUtils; +import org.briarproject.bramble.plugin.file.RemovableDriveModule; import org.briarproject.bramble.plugin.tor.CircumventionProvider; import org.briarproject.bramble.system.ClockModule; import org.briarproject.briar.BriarCoreEagerSingletons; @@ -83,7 +84,8 @@ import dagger.Component; AppModule.class, AttachmentModule.class, ClockModule.class, - MediaModule.class + MediaModule.class, + RemovableDriveModule.class }) public interface AndroidComponent extends BrambleCoreEagerSingletons, BrambleAndroidEagerSingletons, From c9c6f3682c6ae3cd508eded4c234506c05e487a9 Mon Sep 17 00:00:00 2001 From: akwizgran Date: Fri, 7 May 2021 13:45:12 +0100 Subject: [PATCH 2/9] Add task factory. --- .../api/plugin/file/RemovableDriveTask.java | 2 +- .../file/RemovableDriveManagerImpl.java | 14 ++++---- .../plugin/file/RemovableDriveModule.java | 6 ++++ .../file/RemovableDriveTaskFactory.java | 17 +++++++++ .../file/RemovableDriveTaskFactoryImpl.java | 36 +++++++++++++++++++ .../plugin/file/RemovableDriveTaskImpl.java | 2 +- 6 files changed, 67 insertions(+), 10 deletions(-) create mode 100644 bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactory.java create mode 100644 bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java index 08165c267..3bc4c1837 100644 --- a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java @@ -6,7 +6,7 @@ import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import java.io.File; @NotNullByDefault -public interface RemovableDriveTask { +public interface RemovableDriveTask extends Runnable { /** * Returns the file that this task is reading from or writing to. diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveManagerImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveManagerImpl.java index 4b6d9dffc..3752449fa 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveManagerImpl.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveManagerImpl.java @@ -1,7 +1,6 @@ package org.briarproject.bramble.plugin.file; import org.briarproject.bramble.api.contact.ContactId; -import org.briarproject.bramble.api.event.EventExecutor; import org.briarproject.bramble.api.lifecycle.IoExecutor; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.plugin.file.RemovableDriveManager; @@ -20,7 +19,8 @@ import javax.inject.Inject; class RemovableDriveManagerImpl implements RemovableDriveManager, RemovableDriveTaskRegistry { - private final Executor ioExecutor, eventExecutor; + private final Executor ioExecutor; + private final RemovableDriveTaskFactory taskFactory; private final ConcurrentHashMap readers = new ConcurrentHashMap<>(); private final ConcurrentHashMap @@ -28,9 +28,9 @@ class RemovableDriveManagerImpl @Inject RemovableDriveManagerImpl(@IoExecutor Executor ioExecutor, - @EventExecutor Executor eventExecutor) { + RemovableDriveTaskFactory taskFactory) { this.ioExecutor = ioExecutor; - this.eventExecutor = eventExecutor; + this.taskFactory = taskFactory; } @Nullable @@ -47,8 +47,7 @@ class RemovableDriveManagerImpl @Override public RemovableDriveTask startReaderTask(ContactId c, File f) { - RemovableDriverReaderTask task = - new RemovableDriverReaderTask(eventExecutor, this, c, f); + RemovableDriveTask task = taskFactory.createReader(this, c, f); RemovableDriveTask old = readers.putIfAbsent(c, task); if (old == null) { ioExecutor.execute(task); @@ -60,8 +59,7 @@ class RemovableDriveManagerImpl @Override public RemovableDriveTask startWriterTask(ContactId c, File f) { - RemovableDriverWriterTask task = - new RemovableDriverWriterTask(eventExecutor, this, c, f); + RemovableDriveTask task = taskFactory.createWriter(this, c, f); RemovableDriveTask old = writers.putIfAbsent(c, task); if (old == null) { ioExecutor.execute(task); diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveModule.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveModule.java index 92455bb3a..3857cc338 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveModule.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveModule.java @@ -16,4 +16,10 @@ public class RemovableDriveModule { RemovableDriveManagerImpl removableDriveManager) { return removableDriveManager; } + + @Provides + RemovableDriveTaskFactory provideTaskFactory( + RemovableDriveTaskFactoryImpl taskFactory) { + return taskFactory; + } } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactory.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactory.java new file mode 100644 index 000000000..a81f88249 --- /dev/null +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactory.java @@ -0,0 +1,17 @@ +package org.briarproject.bramble.plugin.file; + +import org.briarproject.bramble.api.contact.ContactId; +import org.briarproject.bramble.api.nullsafety.NotNullByDefault; +import org.briarproject.bramble.api.plugin.file.RemovableDriveTask; + +import java.io.File; + +@NotNullByDefault +interface RemovableDriveTaskFactory { + + RemovableDriveTask createReader(RemovableDriveTaskRegistry registry, + ContactId c, File f); + + RemovableDriveTask createWriter(RemovableDriveTaskRegistry registry, + ContactId c, File f); +} diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java new file mode 100644 index 000000000..b46f659d4 --- /dev/null +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java @@ -0,0 +1,36 @@ +package org.briarproject.bramble.plugin.file; + +import org.briarproject.bramble.api.contact.ContactId; +import org.briarproject.bramble.api.event.EventExecutor; +import org.briarproject.bramble.api.nullsafety.NotNullByDefault; +import org.briarproject.bramble.api.plugin.file.RemovableDriveTask; + +import java.io.File; +import java.util.concurrent.Executor; + +import javax.annotation.concurrent.Immutable; +import javax.inject.Inject; + +@Immutable +@NotNullByDefault +class RemovableDriveTaskFactoryImpl implements RemovableDriveTaskFactory { + + private final Executor eventExecutor; + + @Inject + RemovableDriveTaskFactoryImpl(@EventExecutor Executor eventExecutor) { + this.eventExecutor = eventExecutor; + } + + @Override + public RemovableDriveTask createReader(RemovableDriveTaskRegistry registry, + ContactId c, File f) { + return new RemovableDriverReaderTask(eventExecutor, registry, c, f); + } + + @Override + public RemovableDriveTask createWriter(RemovableDriveTaskRegistry registry, + ContactId c, File f) { + return new RemovableDriverWriterTask(eventExecutor, registry, c, f); + } +} diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java index 0af720b77..e5f09f971 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java @@ -14,7 +14,7 @@ import javax.annotation.concurrent.ThreadSafe; @ThreadSafe @NotNullByDefault -abstract class RemovableDriveTaskImpl implements RemovableDriveTask, Runnable { +abstract class RemovableDriveTaskImpl implements RemovableDriveTask { private final Executor eventExecutor; final RemovableDriveTaskRegistry registry; From 2c39b02644f59314b23323102cf6631efc9fbf48 Mon Sep 17 00:00:00 2001 From: akwizgran Date: Fri, 7 May 2021 14:20:30 +0100 Subject: [PATCH 3/9] Implement RemovableDriverReaderTask. --- .../api/plugin/file/RemovableDriveTask.java | 2 +- .../file/RemovableDriveTaskFactoryImpl.java | 21 ++++- .../plugin/file/RemovableDriveTaskImpl.java | 38 +++++++- .../file/RemovableDriverReaderTask.java | 92 +++++++++++++++---- .../file/RemovableDriverWriterTask.java | 15 ++- 5 files changed, 138 insertions(+), 30 deletions(-) diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java index 3bc4c1837..c4f2e00a9 100644 --- a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java @@ -26,7 +26,7 @@ public interface RemovableDriveTask extends Runnable { interface Observer { @EventExecutor - void onProgress(long written, long total); + void onProgress(long done, long total); @EventExecutor void onCompletion(boolean success); diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java index b46f659d4..d8021ff82 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java @@ -1,8 +1,11 @@ package org.briarproject.bramble.plugin.file; +import org.briarproject.bramble.api.connection.ConnectionManager; import org.briarproject.bramble.api.contact.ContactId; +import org.briarproject.bramble.api.event.EventBus; import org.briarproject.bramble.api.event.EventExecutor; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; +import org.briarproject.bramble.api.plugin.PluginManager; import org.briarproject.bramble.api.plugin.file.RemovableDriveTask; import java.io.File; @@ -16,21 +19,33 @@ import javax.inject.Inject; class RemovableDriveTaskFactoryImpl implements RemovableDriveTaskFactory { private final Executor eventExecutor; + private final PluginManager pluginManager; + private final ConnectionManager connectionManager; + private final EventBus eventBus; @Inject - RemovableDriveTaskFactoryImpl(@EventExecutor Executor eventExecutor) { + RemovableDriveTaskFactoryImpl( + @EventExecutor Executor eventExecutor, + PluginManager pluginManager, + ConnectionManager connectionManager, + EventBus eventBus) { this.eventExecutor = eventExecutor; + this.pluginManager = pluginManager; + this.connectionManager = connectionManager; + this.eventBus = eventBus; } @Override public RemovableDriveTask createReader(RemovableDriveTaskRegistry registry, ContactId c, File f) { - return new RemovableDriverReaderTask(eventExecutor, registry, c, f); + return new RemovableDriverReaderTask(eventExecutor, pluginManager, + connectionManager, eventBus, registry, c, f); } @Override public RemovableDriveTask createWriter(RemovableDriveTaskRegistry registry, ContactId c, File f) { - return new RemovableDriverWriterTask(eventExecutor, registry, c, f); + return new RemovableDriverWriterTask(eventExecutor, pluginManager, + connectionManager, eventBus, registry, c, f); } } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java index e5f09f971..4984e3876 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java @@ -1,9 +1,14 @@ package org.briarproject.bramble.plugin.file; import org.briarproject.bramble.api.Consumer; +import org.briarproject.bramble.api.connection.ConnectionManager; import org.briarproject.bramble.api.contact.ContactId; +import org.briarproject.bramble.api.event.EventBus; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; +import org.briarproject.bramble.api.plugin.PluginManager; import org.briarproject.bramble.api.plugin.file.RemovableDriveTask; +import org.briarproject.bramble.api.plugin.simplex.SimplexPlugin; +import org.briarproject.bramble.api.properties.TransportProperties; import java.io.File; import java.util.List; @@ -12,23 +17,38 @@ import java.util.concurrent.Executor; import javax.annotation.concurrent.ThreadSafe; +import static org.briarproject.bramble.api.nullsafety.NullSafety.requireNonNull; +import static org.briarproject.bramble.api.plugin.file.FileConstants.PROP_PATH; +import static org.briarproject.bramble.api.plugin.file.RemovableDriveConstants.ID; + @ThreadSafe @NotNullByDefault abstract class RemovableDriveTaskImpl implements RemovableDriveTask { private final Executor eventExecutor; + private final PluginManager pluginManager; + final ConnectionManager connectionManager; + final EventBus eventBus; final RemovableDriveTaskRegistry registry; final ContactId contactId; final File file; private final List observers = new CopyOnWriteArrayList<>(); - RemovableDriveTaskImpl(Executor eventExecutor, - RemovableDriveTaskRegistry registry, ContactId contactId, + RemovableDriveTaskImpl( + Executor eventExecutor, + PluginManager pluginManager, + ConnectionManager connectionManager, + EventBus eventBus, + RemovableDriveTaskRegistry registry, + ContactId contactId, File file) { + this.eventExecutor = eventExecutor; + this.pluginManager = pluginManager; + this.connectionManager = connectionManager; + this.eventBus = eventBus; + this.registry = registry; this.contactId = contactId; this.file = file; - this.registry = registry; - this.eventExecutor = eventExecutor; } @Override @@ -51,4 +71,14 @@ abstract class RemovableDriveTaskImpl implements RemovableDriveTask { for (Observer o : observers) visitor.accept(o); }); } + + SimplexPlugin getPlugin() { + return (SimplexPlugin) requireNonNull(pluginManager.getPlugin(ID)); + } + + TransportProperties createProperties() { + TransportProperties p = new TransportProperties(); + p.put(PROP_PATH, file.getAbsolutePath()); + return p; + } } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverReaderTask.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverReaderTask.java index 3cc53c7b4..a7374fc53 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverReaderTask.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverReaderTask.java @@ -1,46 +1,100 @@ package org.briarproject.bramble.plugin.file; +import org.briarproject.bramble.api.connection.ConnectionManager; import org.briarproject.bramble.api.contact.ContactId; +import org.briarproject.bramble.api.event.Event; +import org.briarproject.bramble.api.event.EventBus; +import org.briarproject.bramble.api.event.EventListener; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; +import org.briarproject.bramble.api.plugin.PluginManager; +import org.briarproject.bramble.api.plugin.TransportConnectionReader; +import org.briarproject.bramble.api.sync.event.MessageAddedEvent; import java.io.File; -import java.io.FileInputStream; import java.io.IOException; import java.io.InputStream; import java.util.concurrent.Executor; +import java.util.concurrent.atomic.AtomicLong; import java.util.logging.Logger; -import static java.util.logging.Level.WARNING; +import static java.lang.Math.min; import static java.util.logging.Logger.getLogger; -import static org.briarproject.bramble.util.IoUtils.tryToClose; -import static org.briarproject.bramble.util.LogUtils.logException; +import static org.briarproject.bramble.api.plugin.file.RemovableDriveConstants.ID; @NotNullByDefault -class RemovableDriverReaderTask extends RemovableDriveTaskImpl { +class RemovableDriverReaderTask extends RemovableDriveTaskImpl + implements EventListener { private final static Logger LOG = getLogger(RemovableDriverReaderTask.class.getName()); - RemovableDriverReaderTask(Executor eventExecutor, - RemovableDriveTaskRegistry registry, ContactId contactId, + private final AtomicLong fileLength = new AtomicLong(0); + private final AtomicLong totalMessageLength = new AtomicLong(0); + + RemovableDriverReaderTask( + Executor eventExecutor, + PluginManager pluginManager, + ConnectionManager connectionManager, + EventBus eventBus, + RemovableDriveTaskRegistry registry, + ContactId contactId, File file) { - super(eventExecutor, registry, contactId, file); + super(eventExecutor, pluginManager, connectionManager, eventBus, + registry, contactId, file); } @Override public void run() { - // TODO - InputStream in = null; - try { - visitObservers(o -> o.onProgress(0, 100)); - in = new FileInputStream(file); - visitObservers(o -> o.onCompletion(true)); - } catch (IOException e) { - logException(LOG, WARNING, e); + TransportConnectionReader r = + getPlugin().createReader(createProperties()); + if (r == null) { + LOG.warning("Failed to create reader"); + registry.removeReader(contactId, RemovableDriverReaderTask.this); visitObservers(o -> o.onCompletion(false)); - } finally { - tryToClose(in, LOG, WARNING); - registry.removeReader(contactId, this); + return; + } + fileLength.set(file.length()); + eventBus.addListener(this); + connectionManager.manageIncomingConnection(ID, new DecoratedReader(r)); + } + + @Override + public void eventOccurred(Event e) { + if (e instanceof MessageAddedEvent) { + MessageAddedEvent m = (MessageAddedEvent) e; + if (contactId.equals(m.getContactId())) { + LOG.info("Message received"); + updateProgress(m.getMessage().getRawLength()); + } + } + } + + private void updateProgress(int messageLength) { + long done = totalMessageLength.addAndGet(messageLength); + long total = fileLength.get(); + visitObservers(o -> o.onProgress(min(done, total), total)); + } + + private class DecoratedReader implements TransportConnectionReader { + + private final TransportConnectionReader delegate; + + private DecoratedReader(TransportConnectionReader delegate) { + this.delegate = delegate; + } + + @Override + public InputStream getInputStream() throws IOException { + return delegate.getInputStream(); + } + + @Override + public void dispose(boolean exception, boolean recognised) + throws IOException { + delegate.dispose(exception, recognised); + registry.removeReader(contactId, RemovableDriverReaderTask.this); + eventBus.removeListener(RemovableDriverReaderTask.this); + visitObservers(o -> o.onCompletion(!exception && recognised)); } } } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverWriterTask.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverWriterTask.java index ed0715d16..7394b1ac2 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverWriterTask.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverWriterTask.java @@ -1,7 +1,10 @@ package org.briarproject.bramble.plugin.file; +import org.briarproject.bramble.api.connection.ConnectionManager; import org.briarproject.bramble.api.contact.ContactId; +import org.briarproject.bramble.api.event.EventBus; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; +import org.briarproject.bramble.api.plugin.PluginManager; import java.io.File; import java.io.FileOutputStream; @@ -21,10 +24,16 @@ class RemovableDriverWriterTask extends RemovableDriveTaskImpl { private static final Logger LOG = getLogger(RemovableDriverWriterTask.class.getName()); - RemovableDriverWriterTask(Executor eventExecutor, - RemovableDriveTaskRegistry registry, ContactId contactId, + RemovableDriverWriterTask( + Executor eventExecutor, + PluginManager pluginManager, + ConnectionManager connectionManager, + EventBus eventBus, + RemovableDriveTaskRegistry registry, + ContactId contactId, File file) { - super(eventExecutor, registry, contactId, file); + super(eventExecutor, pluginManager, connectionManager, eventBus, + registry, contactId, file); } @Override From 03248d04e5c4df7713dc7be9eaa11d55ec8b05ba Mon Sep 17 00:00:00 2001 From: akwizgran Date: Fri, 7 May 2021 14:31:53 +0100 Subject: [PATCH 4/9] Fix typo in class names. --- ...ReaderTask.java => RemovableDriveReaderTask.java} | 12 ++++++------ .../plugin/file/RemovableDriveTaskFactoryImpl.java | 4 ++-- ...WriterTask.java => RemovableDriveWriterTask.java} | 6 +++--- 3 files changed, 11 insertions(+), 11 deletions(-) rename bramble-core/src/main/java/org/briarproject/bramble/plugin/file/{RemovableDriverReaderTask.java => RemovableDriveReaderTask.java} (89%) rename bramble-core/src/main/java/org/briarproject/bramble/plugin/file/{RemovableDriverWriterTask.java => RemovableDriveWriterTask.java} (91%) diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverReaderTask.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveReaderTask.java similarity index 89% rename from bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverReaderTask.java rename to bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveReaderTask.java index a7374fc53..2e0f02e0b 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverReaderTask.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveReaderTask.java @@ -22,16 +22,16 @@ import static java.util.logging.Logger.getLogger; import static org.briarproject.bramble.api.plugin.file.RemovableDriveConstants.ID; @NotNullByDefault -class RemovableDriverReaderTask extends RemovableDriveTaskImpl +class RemovableDriveReaderTask extends RemovableDriveTaskImpl implements EventListener { private final static Logger LOG = - getLogger(RemovableDriverReaderTask.class.getName()); + getLogger(RemovableDriveReaderTask.class.getName()); private final AtomicLong fileLength = new AtomicLong(0); private final AtomicLong totalMessageLength = new AtomicLong(0); - RemovableDriverReaderTask( + RemovableDriveReaderTask( Executor eventExecutor, PluginManager pluginManager, ConnectionManager connectionManager, @@ -49,7 +49,7 @@ class RemovableDriverReaderTask extends RemovableDriveTaskImpl getPlugin().createReader(createProperties()); if (r == null) { LOG.warning("Failed to create reader"); - registry.removeReader(contactId, RemovableDriverReaderTask.this); + registry.removeReader(contactId, RemovableDriveReaderTask.this); visitObservers(o -> o.onCompletion(false)); return; } @@ -92,8 +92,8 @@ class RemovableDriverReaderTask extends RemovableDriveTaskImpl public void dispose(boolean exception, boolean recognised) throws IOException { delegate.dispose(exception, recognised); - registry.removeReader(contactId, RemovableDriverReaderTask.this); - eventBus.removeListener(RemovableDriverReaderTask.this); + registry.removeReader(contactId, RemovableDriveReaderTask.this); + eventBus.removeListener(RemovableDriveReaderTask.this); visitObservers(o -> o.onCompletion(!exception && recognised)); } } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java index d8021ff82..ad1f6ee06 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java @@ -38,14 +38,14 @@ class RemovableDriveTaskFactoryImpl implements RemovableDriveTaskFactory { @Override public RemovableDriveTask createReader(RemovableDriveTaskRegistry registry, ContactId c, File f) { - return new RemovableDriverReaderTask(eventExecutor, pluginManager, + return new RemovableDriveReaderTask(eventExecutor, pluginManager, connectionManager, eventBus, registry, c, f); } @Override public RemovableDriveTask createWriter(RemovableDriveTaskRegistry registry, ContactId c, File f) { - return new RemovableDriverWriterTask(eventExecutor, pluginManager, + return new RemovableDriveWriterTask(eventExecutor, pluginManager, connectionManager, eventBus, registry, c, f); } } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverWriterTask.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java similarity index 91% rename from bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverWriterTask.java rename to bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java index 7394b1ac2..858d6a19c 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriverWriterTask.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java @@ -19,12 +19,12 @@ import static org.briarproject.bramble.util.IoUtils.tryToClose; import static org.briarproject.bramble.util.LogUtils.logException; @NotNullByDefault -class RemovableDriverWriterTask extends RemovableDriveTaskImpl { +class RemovableDriveWriterTask extends RemovableDriveTaskImpl { private static final Logger LOG = - getLogger(RemovableDriverWriterTask.class.getName()); + getLogger(RemovableDriveWriterTask.class.getName()); - RemovableDriverWriterTask( + RemovableDriveWriterTask( Executor eventExecutor, PluginManager pluginManager, ConnectionManager connectionManager, From e420201b00f31f3ace4fb25a4d2a41b12aa0cb55 Mon Sep 17 00:00:00 2001 From: akwizgran Date: Fri, 7 May 2021 14:48:25 +0100 Subject: [PATCH 5/9] Implement RemovableDriveWriterTask, except for progress updates. --- .../plugin/file/RemovableDriveReaderTask.java | 15 +--- .../file/RemovableDriveTaskFactoryImpl.java | 6 +- .../plugin/file/RemovableDriveTaskImpl.java | 10 +++ .../plugin/file/RemovableDriveWriterTask.java | 84 +++++++++++++++---- 4 files changed, 85 insertions(+), 30 deletions(-) diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveReaderTask.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveReaderTask.java index 2e0f02e0b..e51743332 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveReaderTask.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveReaderTask.java @@ -14,10 +14,8 @@ import java.io.File; import java.io.IOException; import java.io.InputStream; import java.util.concurrent.Executor; -import java.util.concurrent.atomic.AtomicLong; import java.util.logging.Logger; -import static java.lang.Math.min; import static java.util.logging.Logger.getLogger; import static org.briarproject.bramble.api.plugin.file.RemovableDriveConstants.ID; @@ -28,9 +26,6 @@ class RemovableDriveReaderTask extends RemovableDriveTaskImpl private final static Logger LOG = getLogger(RemovableDriveReaderTask.class.getName()); - private final AtomicLong fileLength = new AtomicLong(0); - private final AtomicLong totalMessageLength = new AtomicLong(0); - RemovableDriveReaderTask( Executor eventExecutor, PluginManager pluginManager, @@ -49,11 +44,11 @@ class RemovableDriveReaderTask extends RemovableDriveTaskImpl getPlugin().createReader(createProperties()); if (r == null) { LOG.warning("Failed to create reader"); - registry.removeReader(contactId, RemovableDriveReaderTask.this); + registry.removeReader(contactId, this); visitObservers(o -> o.onCompletion(false)); return; } - fileLength.set(file.length()); + progressTotal.set(file.length()); eventBus.addListener(this); connectionManager.manageIncomingConnection(ID, new DecoratedReader(r)); } @@ -69,12 +64,6 @@ class RemovableDriveReaderTask extends RemovableDriveTaskImpl } } - private void updateProgress(int messageLength) { - long done = totalMessageLength.addAndGet(messageLength); - long total = fileLength.get(); - visitObservers(o -> o.onProgress(min(done, total), total)); - } - private class DecoratedReader implements TransportConnectionReader { private final TransportConnectionReader delegate; diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java index ad1f6ee06..dbf4b3bc7 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java @@ -2,6 +2,7 @@ package org.briarproject.bramble.plugin.file; import org.briarproject.bramble.api.connection.ConnectionManager; import org.briarproject.bramble.api.contact.ContactId; +import org.briarproject.bramble.api.db.DatabaseComponent; import org.briarproject.bramble.api.event.EventBus; import org.briarproject.bramble.api.event.EventExecutor; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; @@ -18,6 +19,7 @@ import javax.inject.Inject; @NotNullByDefault class RemovableDriveTaskFactoryImpl implements RemovableDriveTaskFactory { + private final DatabaseComponent db; private final Executor eventExecutor; private final PluginManager pluginManager; private final ConnectionManager connectionManager; @@ -25,10 +27,12 @@ class RemovableDriveTaskFactoryImpl implements RemovableDriveTaskFactory { @Inject RemovableDriveTaskFactoryImpl( + DatabaseComponent db, @EventExecutor Executor eventExecutor, PluginManager pluginManager, ConnectionManager connectionManager, EventBus eventBus) { + this.db = db; this.eventExecutor = eventExecutor; this.pluginManager = pluginManager; this.connectionManager = connectionManager; @@ -45,7 +49,7 @@ class RemovableDriveTaskFactoryImpl implements RemovableDriveTaskFactory { @Override public RemovableDriveTask createWriter(RemovableDriveTaskRegistry registry, ContactId c, File f) { - return new RemovableDriveWriterTask(eventExecutor, pluginManager, + return new RemovableDriveWriterTask(db, eventExecutor, pluginManager, connectionManager, eventBus, registry, c, f); } } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java index 4984e3876..f7a919ed7 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java @@ -14,9 +14,11 @@ import java.io.File; import java.util.List; import java.util.concurrent.CopyOnWriteArrayList; import java.util.concurrent.Executor; +import java.util.concurrent.atomic.AtomicLong; import javax.annotation.concurrent.ThreadSafe; +import static java.lang.Math.min; import static org.briarproject.bramble.api.nullsafety.NullSafety.requireNonNull; import static org.briarproject.bramble.api.plugin.file.FileConstants.PROP_PATH; import static org.briarproject.bramble.api.plugin.file.RemovableDriveConstants.ID; @@ -33,6 +35,8 @@ abstract class RemovableDriveTaskImpl implements RemovableDriveTask { final ContactId contactId; final File file; private final List observers = new CopyOnWriteArrayList<>(); + final AtomicLong progressTotal = new AtomicLong(0); + private final AtomicLong progressDone = new AtomicLong(0); RemovableDriveTaskImpl( Executor eventExecutor, @@ -81,4 +85,10 @@ abstract class RemovableDriveTaskImpl implements RemovableDriveTask { p.put(PROP_PATH, file.getAbsolutePath()); return p; } + + void updateProgress(long progress) { + long done = progressDone.addAndGet(progress); + long total = progressTotal.get(); + visitObservers(o -> o.onProgress(min(done, total), total)); + } } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java index 858d6a19c..671921607 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java @@ -2,29 +2,36 @@ package org.briarproject.bramble.plugin.file; import org.briarproject.bramble.api.connection.ConnectionManager; import org.briarproject.bramble.api.contact.ContactId; +import org.briarproject.bramble.api.db.DatabaseComponent; +import org.briarproject.bramble.api.event.Event; import org.briarproject.bramble.api.event.EventBus; +import org.briarproject.bramble.api.event.EventListener; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.plugin.PluginManager; +import org.briarproject.bramble.api.plugin.TransportConnectionWriter; +import org.briarproject.bramble.api.sync.event.MessagesSentEvent; import java.io.File; -import java.io.FileOutputStream; import java.io.IOException; import java.io.OutputStream; import java.util.concurrent.Executor; import java.util.logging.Logger; -import static java.util.logging.Level.WARNING; +import static java.util.logging.Level.INFO; import static java.util.logging.Logger.getLogger; -import static org.briarproject.bramble.util.IoUtils.tryToClose; -import static org.briarproject.bramble.util.LogUtils.logException; +import static org.briarproject.bramble.api.plugin.file.RemovableDriveConstants.ID; @NotNullByDefault -class RemovableDriveWriterTask extends RemovableDriveTaskImpl { +class RemovableDriveWriterTask extends RemovableDriveTaskImpl + implements EventListener { private static final Logger LOG = getLogger(RemovableDriveWriterTask.class.getName()); + private final DatabaseComponent db; + RemovableDriveWriterTask( + DatabaseComponent db, Executor eventExecutor, PluginManager pluginManager, ConnectionManager connectionManager, @@ -34,22 +41,67 @@ class RemovableDriveWriterTask extends RemovableDriveTaskImpl { File file) { super(eventExecutor, pluginManager, connectionManager, eventBus, registry, contactId, file); + this.db = db; } @Override public void run() { - // TODO - OutputStream out = null; - try { - visitObservers(o -> o.onProgress(0, 100)); - out = new FileOutputStream(file); - visitObservers(o -> o.onCompletion(true)); - } catch (IOException e) { - logException(LOG, WARNING, e); - visitObservers(o -> o.onCompletion(false)); - } finally { - tryToClose(out, LOG, WARNING); + TransportConnectionWriter w = + getPlugin().createWriter(createProperties()); + if (w == null) { + LOG.warning("Failed to create writer"); registry.removeWriter(contactId, this); + visitObservers(o -> o.onCompletion(false)); + return; + } + // TODO: Get total bytes to send from DB + eventBus.addListener(this); + connectionManager.manageOutgoingConnection(contactId, ID, + new DecoratedWriter(w)); + } + + @Override + public void eventOccurred(Event e) { + if (e instanceof MessagesSentEvent) { + MessagesSentEvent m = (MessagesSentEvent) e; + if (contactId.equals(m.getContactId())) { + if (LOG.isLoggable(INFO)) { + LOG.info(m.getMessageIds().size() + " messages sent"); + } + // TODO: Update progress + } + } + } + + private class DecoratedWriter implements TransportConnectionWriter { + + private final TransportConnectionWriter delegate; + + private DecoratedWriter(TransportConnectionWriter delegate) { + this.delegate = delegate; + } + + @Override + public int getMaxLatency() { + return delegate.getMaxLatency(); + } + + @Override + public int getMaxIdleTime() { + return delegate.getMaxIdleTime(); + } + + @Override + public OutputStream getOutputStream() throws IOException { + return delegate.getOutputStream(); + } + + @Override + public void dispose(boolean exception) throws IOException { + delegate.dispose(exception); + registry.removeWriter(contactId, RemovableDriveWriterTask.this); + eventBus.removeListener(RemovableDriveWriterTask.this); + visitObservers(o -> o.onCompletion(!exception)); } } } From bca6f1506ea23954d8e774f3fb65eda0e8f540c4 Mon Sep 17 00:00:00 2001 From: akwizgran Date: Fri, 7 May 2021 16:02:09 +0100 Subject: [PATCH 6/9] Add integration test for syncing via removable drives. --- .../file/RemovableDriveIntegrationTest.java | 177 ++++++++++++++++++ ...emovableDriveIntegrationTestComponent.java | 53 ++++++ .../RemovableDriveIntegrationTestModule.java | 81 ++++++++ 3 files changed, 311 insertions(+) create mode 100644 bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTest.java create mode 100644 bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTestComponent.java create mode 100644 bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTestModule.java diff --git a/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTest.java b/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTest.java new file mode 100644 index 000000000..acd4844dc --- /dev/null +++ b/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTest.java @@ -0,0 +1,177 @@ +package org.briarproject.bramble.plugin.file; + +import org.briarproject.bramble.api.contact.ContactId; +import org.briarproject.bramble.api.contact.ContactManager; +import org.briarproject.bramble.api.crypto.SecretKey; +import org.briarproject.bramble.api.event.Event; +import org.briarproject.bramble.api.event.EventListener; +import org.briarproject.bramble.api.identity.Author; +import org.briarproject.bramble.api.identity.Identity; +import org.briarproject.bramble.api.identity.IdentityManager; +import org.briarproject.bramble.api.lifecycle.LifecycleManager; +import org.briarproject.bramble.api.nullsafety.NotNullByDefault; +import org.briarproject.bramble.api.plugin.file.RemovableDriveTask; +import org.briarproject.bramble.api.plugin.file.RemovableDriveTask.Observer; +import org.briarproject.bramble.api.sync.event.MessageStateChangedEvent; +import org.briarproject.bramble.test.BrambleTestCase; +import org.briarproject.bramble.test.TestDatabaseConfigModule; +import org.junit.After; +import org.junit.Before; +import org.junit.Test; + +import java.io.File; +import java.util.concurrent.CountDownLatch; + +import static java.util.concurrent.TimeUnit.MILLISECONDS; +import static org.briarproject.bramble.api.sync.validation.MessageState.DELIVERED; +import static org.briarproject.bramble.test.TestUtils.deleteTestDirectory; +import static org.briarproject.bramble.test.TestUtils.getSecretKey; +import static org.briarproject.bramble.test.TestUtils.getTestDirectory; +import static org.junit.Assert.assertTrue; + +public class RemovableDriveIntegrationTest extends BrambleTestCase { + + private static final int TIMEOUT_MS = 5_000; + + private final File testDir = getTestDirectory(); + private final File aliceDir = new File(testDir, "alice"); + private final File bobDir = new File(testDir, "bob"); + + private final SecretKey rootKey = getSecretKey(); + private final long timestamp = System.currentTimeMillis(); + + private RemovableDriveIntegrationTestComponent alice, bob; + + @Before + public void setUp() { + assertTrue(testDir.mkdirs()); + alice = DaggerRemovableDriveIntegrationTestComponent.builder() + .testDatabaseConfigModule( + new TestDatabaseConfigModule(aliceDir)).build(); + RemovableDriveIntegrationTestComponent.Helper + .injectEagerSingletons(alice); + bob = DaggerRemovableDriveIntegrationTestComponent.builder() + .testDatabaseConfigModule( + new TestDatabaseConfigModule(bobDir)).build(); + RemovableDriveIntegrationTestComponent.Helper + .injectEagerSingletons(bob); + } + + @Test + public void testWriteAndRead() throws Exception { + // Create the identities + Identity aliceIdentity = + alice.getIdentityManager().createIdentity("Alice"); + Identity bobIdentity = bob.getIdentityManager().createIdentity("Bob"); + // Set up the devices and get the contact IDs + ContactId bobId = setUp(alice, aliceIdentity, + bobIdentity.getLocalAuthor(), true); + ContactId aliceId = setUp(bob, bobIdentity, + aliceIdentity.getLocalAuthor(), false); + // Sync Alice's client versions and transport properties + read(bob, aliceId, write(alice, bobId), 2); + // Sync Bob's client versions and transport properties + read(alice, bobId, write(bob, aliceId), 2); + } + + private ContactId setUp(RemovableDriveIntegrationTestComponent device, + Identity local, Author remote, boolean alice) throws Exception { + // Add an identity for the user + IdentityManager identityManager = device.getIdentityManager(); + identityManager.registerIdentity(local); + // Start the lifecycle manager + LifecycleManager lifecycleManager = device.getLifecycleManager(); + lifecycleManager.startServices(getSecretKey()); + lifecycleManager.waitForStartup(); + // Add the other user as a contact + ContactManager contactManager = device.getContactManager(); + return contactManager.addContact(remote, local.getId(), rootKey, + timestamp, alice, true, true); + } + + @SuppressWarnings("SameParameterValue") + private void read(RemovableDriveIntegrationTestComponent device, + ContactId contactId, File file, int deliveries) throws Exception { + // Listen for message deliveries + MessageDeliveryListener listener = + new MessageDeliveryListener(deliveries); + device.getEventBus().addListener(listener); + // Read the incoming stream + RemovableDriveTask reader = device.getRemovableDriveManager() + .startReaderTask(contactId, file); + CountDownLatch disposedLatch = new CountDownLatch(1); + reader.addObserver(new Observer() { + @Override + public void onProgress(long done, long total) { + } + + @Override + public void onCompletion(boolean success) { + disposedLatch.countDown(); + } + }); + // Wait for the messages to be delivered + assertTrue(listener.delivered.await(TIMEOUT_MS, MILLISECONDS)); + // Clean up the listener + device.getEventBus().removeListener(listener); + // Wait for the reader to be disposed + disposedLatch.await(TIMEOUT_MS, MILLISECONDS); + } + + private File write(RemovableDriveIntegrationTestComponent device, + ContactId contactId) throws Exception { + // Write the outgoing stream to a file + File file = File.createTempFile("sync", ".tmp", testDir); + RemovableDriveTask writer = device.getRemovableDriveManager() + .startWriterTask(contactId, file); + CountDownLatch disposedLatch = new CountDownLatch(1); + writer.addObserver(new Observer() { + @Override + public void onProgress(long done, long total) { + } + + @Override + public void onCompletion(boolean success) { + disposedLatch.countDown(); + } + }); + // Wait for the writer to be disposed + disposedLatch.await(TIMEOUT_MS, MILLISECONDS); + // Return the file containing the stream + return file; + } + + private void tearDown(RemovableDriveIntegrationTestComponent device) + throws Exception { + // Stop the lifecycle manager + LifecycleManager lifecycleManager = device.getLifecycleManager(); + lifecycleManager.stopServices(); + lifecycleManager.waitForShutdown(); + } + + @After + public void tearDown() throws Exception { + // Tear down the devices + tearDown(alice); + tearDown(bob); + deleteTestDirectory(testDir); + } + + @NotNullByDefault + private static class MessageDeliveryListener implements EventListener { + + private final CountDownLatch delivered; + + private MessageDeliveryListener(int deliveries) { + delivered = new CountDownLatch(deliveries); + } + + @Override + public void eventOccurred(Event e) { + if (e instanceof MessageStateChangedEvent) { + MessageStateChangedEvent m = (MessageStateChangedEvent) e; + if (m.getState().equals(DELIVERED)) delivered.countDown(); + } + } + } +} diff --git a/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTestComponent.java b/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTestComponent.java new file mode 100644 index 000000000..9c5c3153d --- /dev/null +++ b/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTestComponent.java @@ -0,0 +1,53 @@ +package org.briarproject.bramble.plugin.file; + +import org.briarproject.bramble.BrambleCoreEagerSingletons; +import org.briarproject.bramble.BrambleCoreModule; +import org.briarproject.bramble.api.contact.ContactManager; +import org.briarproject.bramble.api.event.EventBus; +import org.briarproject.bramble.api.identity.IdentityManager; +import org.briarproject.bramble.api.lifecycle.LifecycleManager; +import org.briarproject.bramble.api.plugin.file.RemovableDriveManager; +import org.briarproject.bramble.battery.DefaultBatteryManagerModule; +import org.briarproject.bramble.event.DefaultEventExecutorModule; +import org.briarproject.bramble.system.DefaultWakefulIoExecutorModule; +import org.briarproject.bramble.system.TimeTravelModule; +import org.briarproject.bramble.test.TestDatabaseConfigModule; +import org.briarproject.bramble.test.TestSecureRandomModule; + +import javax.inject.Singleton; + +import dagger.Component; + +@Singleton +@Component(modules = { + BrambleCoreModule.class, + DefaultBatteryManagerModule.class, + DefaultEventExecutorModule.class, + DefaultWakefulIoExecutorModule.class, + TestDatabaseConfigModule.class, + RemovableDriveIntegrationTestModule.class, + RemovableDriveModule.class, + TestSecureRandomModule.class, + TimeTravelModule.class +}) +interface RemovableDriveIntegrationTestComponent + extends BrambleCoreEagerSingletons { + + ContactManager getContactManager(); + + EventBus getEventBus(); + + IdentityManager getIdentityManager(); + + LifecycleManager getLifecycleManager(); + + RemovableDriveManager getRemovableDriveManager(); + + class Helper { + + public static void injectEagerSingletons( + RemovableDriveIntegrationTestComponent c) { + BrambleCoreEagerSingletons.Helper.injectEagerSingletons(c); + } + } +} diff --git a/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTestModule.java b/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTestModule.java new file mode 100644 index 000000000..7b4699e10 --- /dev/null +++ b/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTestModule.java @@ -0,0 +1,81 @@ +package org.briarproject.bramble.plugin.file; + +import org.briarproject.bramble.api.FeatureFlags; +import org.briarproject.bramble.api.nullsafety.NotNullByDefault; +import org.briarproject.bramble.api.plugin.PluginConfig; +import org.briarproject.bramble.api.plugin.TransportId; +import org.briarproject.bramble.api.plugin.duplex.DuplexPluginFactory; +import org.briarproject.bramble.api.plugin.simplex.SimplexPluginFactory; + +import java.util.Collection; +import java.util.List; +import java.util.Map; + +import javax.inject.Singleton; + +import dagger.Module; +import dagger.Provides; + +import static java.util.Collections.emptyList; +import static java.util.Collections.emptyMap; +import static java.util.Collections.singletonList; + +@Module +class RemovableDriveIntegrationTestModule { + + @Provides + @Singleton + PluginConfig providePluginConfig(RemovableDrivePluginFactory drive) { + @NotNullByDefault + PluginConfig pluginConfig = new PluginConfig() { + + @Override + public Collection getDuplexFactories() { + return emptyList(); + } + + @Override + public Collection getSimplexFactories() { + return singletonList(drive); + } + + @Override + public boolean shouldPoll() { + return false; + } + + @Override + public Map> getTransportPreferences() { + return emptyMap(); + } + + }; + return pluginConfig; + } + + @Provides + FeatureFlags provideFeatureFlags() { + return new FeatureFlags() { + + @Override + public boolean shouldEnableImageAttachments() { + return true; + } + + @Override + public boolean shouldEnableProfilePictures() { + return true; + } + + @Override + public boolean shouldEnableDisappearingMessages() { + return true; + } + + @Override + public boolean shouldEnableConnectViaBluetooth() { + return true; + } + }; + } +} From a198e7d08eadd8ddb9bfa63afa542f7bbb4a24a1 Mon Sep 17 00:00:00 2001 From: akwizgran Date: Fri, 7 May 2021 16:30:53 +0100 Subject: [PATCH 7/9] Ensure that observers see the final state even if they're added late. --- .../api/plugin/file/RemovableDriveTask.java | 40 ++++++++--- .../plugin/file/RemovableDriveReaderTask.java | 8 +-- .../plugin/file/RemovableDriveTaskImpl.java | 72 ++++++++++++++----- .../plugin/file/RemovableDriveWriterTask.java | 4 +- .../file/RemovableDriveIntegrationTest.java | 23 ++---- 5 files changed, 94 insertions(+), 53 deletions(-) diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java index c4f2e00a9..5388dab31 100644 --- a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java @@ -1,6 +1,6 @@ package org.briarproject.bramble.api.plugin.file; -import org.briarproject.bramble.api.event.EventExecutor; +import org.briarproject.bramble.api.Consumer; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import java.io.File; @@ -14,21 +14,43 @@ public interface RemovableDriveTask extends Runnable { File getFile(); /** - * Adds an observer to the task. + * Adds an observer to the task. The observer will be notified of state + * changes on the event thread. If the task has already finished, the + * observer will be notified of its final state. */ - void addObserver(Observer o); + void addObserver(Consumer observer); /** * Removes an observer from the task. */ - void removeObserver(Observer o); + void removeObserver(Consumer observer); - interface Observer { + class State { - @EventExecutor - void onProgress(long done, long total); + private final long done, total; + private final boolean finished, success; - @EventExecutor - void onCompletion(boolean success); + public State(long done, long total, boolean finished, boolean success) { + this.done = done; + this.total = total; + this.finished = finished; + this.success = success; + } + + public long getDone() { + return done; + } + + public long getTotal() { + return total; + } + + public boolean isFinished() { + return finished; + } + + public boolean isSuccess() { + return success; + } } } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveReaderTask.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveReaderTask.java index e51743332..cc93c9099 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveReaderTask.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveReaderTask.java @@ -45,10 +45,10 @@ class RemovableDriveReaderTask extends RemovableDriveTaskImpl if (r == null) { LOG.warning("Failed to create reader"); registry.removeReader(contactId, this); - visitObservers(o -> o.onCompletion(false)); + setSuccess(false); return; } - progressTotal.set(file.length()); + setTotal(file.length()); eventBus.addListener(this); connectionManager.manageIncomingConnection(ID, new DecoratedReader(r)); } @@ -59,7 +59,7 @@ class RemovableDriveReaderTask extends RemovableDriveTaskImpl MessageAddedEvent m = (MessageAddedEvent) e; if (contactId.equals(m.getContactId())) { LOG.info("Message received"); - updateProgress(m.getMessage().getRawLength()); + addDone(m.getMessage().getRawLength()); } } } @@ -83,7 +83,7 @@ class RemovableDriveReaderTask extends RemovableDriveTaskImpl delegate.dispose(exception, recognised); registry.removeReader(contactId, RemovableDriveReaderTask.this); eventBus.removeListener(RemovableDriveReaderTask.this); - visitObservers(o -> o.onCompletion(!exception && recognised)); + setSuccess(!exception && recognised); } } } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java index f7a919ed7..de792f644 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java @@ -11,11 +11,11 @@ import org.briarproject.bramble.api.plugin.simplex.SimplexPlugin; import org.briarproject.bramble.api.properties.TransportProperties; import java.io.File; +import java.util.ArrayList; import java.util.List; -import java.util.concurrent.CopyOnWriteArrayList; import java.util.concurrent.Executor; -import java.util.concurrent.atomic.AtomicLong; +import javax.annotation.concurrent.GuardedBy; import javax.annotation.concurrent.ThreadSafe; import static java.lang.Math.min; @@ -34,9 +34,12 @@ abstract class RemovableDriveTaskImpl implements RemovableDriveTask { final RemovableDriveTaskRegistry registry; final ContactId contactId; final File file; - private final List observers = new CopyOnWriteArrayList<>(); - final AtomicLong progressTotal = new AtomicLong(0); - private final AtomicLong progressDone = new AtomicLong(0); + + private final Object lock = new Object(); + @GuardedBy("lock") + private final List> observers = new ArrayList<>(); + @GuardedBy("lock") + private State state = new State(0, 0, false, false); RemovableDriveTaskImpl( Executor eventExecutor, @@ -61,19 +64,22 @@ abstract class RemovableDriveTaskImpl implements RemovableDriveTask { } @Override - public void addObserver(Observer o) { - observers.add(o); + public void addObserver(Consumer o) { + State state; + synchronized (lock) { + observers.add(o); + state = this.state; + } + if (state.isFinished()) { + eventExecutor.execute(() -> o.accept(state)); + } } @Override - public void removeObserver(Observer o) { - observers.remove(o); - } - - void visitObservers(Consumer visitor) { - eventExecutor.execute(() -> { - for (Observer o : observers) visitor.accept(o); - }); + public void removeObserver(Consumer o) { + synchronized (lock) { + observers.remove(o); + } } SimplexPlugin getPlugin() { @@ -86,9 +92,37 @@ abstract class RemovableDriveTaskImpl implements RemovableDriveTask { return p; } - void updateProgress(long progress) { - long done = progressDone.addAndGet(progress); - long total = progressTotal.get(); - visitObservers(o -> o.onProgress(min(done, total), total)); + void setTotal(long total) { + synchronized (lock) { + state = new State(state.getDone(), total, state.isFinished(), + state.isSuccess()); + notifyObservers(); + } + } + + void addDone(long done) { + synchronized (lock) { + // Done and total come from different sources; make them consistent + done = min(state.getDone() + done, state.getTotal()); + state = new State(done, state.getTotal(), state.isFinished(), + state.isSuccess()); + } + notifyObservers(); + } + + void setSuccess(boolean success) { + synchronized (lock) { + state = new State(state.getDone(), state.getTotal(), true, success); + } + notifyObservers(); + } + + @GuardedBy("lock") + private void notifyObservers() { + List> observers = new ArrayList<>(this.observers); + State state = this.state; + eventExecutor.execute(() -> { + for (Consumer o : observers) o.accept(state); + }); } } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java index 671921607..ec02e417b 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java @@ -51,7 +51,7 @@ class RemovableDriveWriterTask extends RemovableDriveTaskImpl if (w == null) { LOG.warning("Failed to create writer"); registry.removeWriter(contactId, this); - visitObservers(o -> o.onCompletion(false)); + setSuccess(false); return; } // TODO: Get total bytes to send from DB @@ -101,7 +101,7 @@ class RemovableDriveWriterTask extends RemovableDriveTaskImpl delegate.dispose(exception); registry.removeWriter(contactId, RemovableDriveWriterTask.this); eventBus.removeListener(RemovableDriveWriterTask.this); - visitObservers(o -> o.onCompletion(!exception)); + setSuccess(!exception); } } } diff --git a/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTest.java b/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTest.java index acd4844dc..56a40bcbe 100644 --- a/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTest.java +++ b/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTest.java @@ -11,7 +11,6 @@ import org.briarproject.bramble.api.identity.IdentityManager; import org.briarproject.bramble.api.lifecycle.LifecycleManager; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.plugin.file.RemovableDriveTask; -import org.briarproject.bramble.api.plugin.file.RemovableDriveTask.Observer; import org.briarproject.bramble.api.sync.event.MessageStateChangedEvent; import org.briarproject.bramble.test.BrambleTestCase; import org.briarproject.bramble.test.TestDatabaseConfigModule; @@ -100,15 +99,8 @@ public class RemovableDriveIntegrationTest extends BrambleTestCase { RemovableDriveTask reader = device.getRemovableDriveManager() .startReaderTask(contactId, file); CountDownLatch disposedLatch = new CountDownLatch(1); - reader.addObserver(new Observer() { - @Override - public void onProgress(long done, long total) { - } - - @Override - public void onCompletion(boolean success) { - disposedLatch.countDown(); - } + reader.addObserver(state -> { + if (state.isFinished()) disposedLatch.countDown(); }); // Wait for the messages to be delivered assertTrue(listener.delivered.await(TIMEOUT_MS, MILLISECONDS)); @@ -125,15 +117,8 @@ public class RemovableDriveIntegrationTest extends BrambleTestCase { RemovableDriveTask writer = device.getRemovableDriveManager() .startWriterTask(contactId, file); CountDownLatch disposedLatch = new CountDownLatch(1); - writer.addObserver(new Observer() { - @Override - public void onProgress(long done, long total) { - } - - @Override - public void onCompletion(boolean success) { - disposedLatch.countDown(); - } + writer.addObserver(state -> { + if (state.isFinished()) disposedLatch.countDown(); }); // Wait for the writer to be disposed disposedLatch.await(TIMEOUT_MS, MILLISECONDS); From 0ce0551f0d82ddaf92fb79dfbfa952cd0e54bb4e Mon Sep 17 00:00:00 2001 From: akwizgran Date: Mon, 10 May 2021 14:14:10 +0100 Subject: [PATCH 8/9] Update progress of writer task. --- .../plugin/file/RemovableDriveWriterTask.java | 21 +++++++++++++++---- 1 file changed, 17 insertions(+), 4 deletions(-) diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java index ec02e417b..d9a9ed75c 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java @@ -3,12 +3,14 @@ package org.briarproject.bramble.plugin.file; import org.briarproject.bramble.api.connection.ConnectionManager; import org.briarproject.bramble.api.contact.ContactId; import org.briarproject.bramble.api.db.DatabaseComponent; +import org.briarproject.bramble.api.db.DbException; import org.briarproject.bramble.api.event.Event; import org.briarproject.bramble.api.event.EventBus; import org.briarproject.bramble.api.event.EventListener; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.plugin.PluginManager; import org.briarproject.bramble.api.plugin.TransportConnectionWriter; +import org.briarproject.bramble.api.plugin.simplex.SimplexPlugin; import org.briarproject.bramble.api.sync.event.MessagesSentEvent; import java.io.File; @@ -18,8 +20,10 @@ import java.util.concurrent.Executor; import java.util.logging.Logger; import static java.util.logging.Level.INFO; +import static java.util.logging.Level.WARNING; import static java.util.logging.Logger.getLogger; import static org.briarproject.bramble.api.plugin.file.RemovableDriveConstants.ID; +import static org.briarproject.bramble.util.LogUtils.logException; @NotNullByDefault class RemovableDriveWriterTask extends RemovableDriveTaskImpl @@ -46,15 +50,24 @@ class RemovableDriveWriterTask extends RemovableDriveTaskImpl @Override public void run() { - TransportConnectionWriter w = - getPlugin().createWriter(createProperties()); + SimplexPlugin plugin = getPlugin(); + TransportConnectionWriter w = plugin.createWriter(createProperties()); if (w == null) { LOG.warning("Failed to create writer"); registry.removeWriter(contactId, this); setSuccess(false); return; } - // TODO: Get total bytes to send from DB + int maxLatency = plugin.getMaxLatency(); + try { + setTotal(db.transactionWithResult(true, txn -> + db.getMessageBytesToSend(txn, contactId, maxLatency))); + } catch (DbException e) { + logException(LOG, WARNING, e); + registry.removeWriter(contactId, this); + setSuccess(false); + return; + } eventBus.addListener(this); connectionManager.manageOutgoingConnection(contactId, ID, new DecoratedWriter(w)); @@ -68,7 +81,7 @@ class RemovableDriveWriterTask extends RemovableDriveTaskImpl if (LOG.isLoggable(INFO)) { LOG.info(m.getMessageIds().size() + " messages sent"); } - // TODO: Update progress + addDone(m.getTotalLength()); } } } From eae329cdfad5411e6851aeb2c1a0899682663e43 Mon Sep 17 00:00:00 2001 From: akwizgran Date: Mon, 10 May 2021 14:36:01 +0100 Subject: [PATCH 9/9] Refactor manager and tasks to remove reliance on files. --- .../api/plugin/file/RemovableDriveManager.java | 17 +++++++++-------- .../api/plugin/file/RemovableDriveTask.java | 17 +++++++++++++---- .../plugin/file/RemovableDriveManagerImpl.java | 12 +++++++----- .../plugin/file/RemovableDriveReaderTask.java | 9 ++++----- .../plugin/file/RemovableDriveTaskFactory.java | 7 +++---- .../file/RemovableDriveTaskFactoryImpl.java | 10 +++++----- .../plugin/file/RemovableDriveTaskImpl.java | 18 +++++------------- .../plugin/file/RemovableDriveWriterTask.java | 8 ++++---- .../file/RemovableDriveIntegrationTest.java | 10 ++++++++-- 9 files changed, 58 insertions(+), 50 deletions(-) diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveManager.java b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveManager.java index 241582dab..081b4362a 100644 --- a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveManager.java +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveManager.java @@ -2,8 +2,7 @@ package org.briarproject.bramble.api.plugin.file; import org.briarproject.bramble.api.contact.ContactId; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; - -import java.io.File; +import org.briarproject.bramble.api.properties.TransportProperties; import javax.annotation.Nullable; @@ -26,15 +25,17 @@ public interface RemovableDriveManager { /** * Starts and returns a reader task for the given contact, reading from - * the given file. If a reader task for the contact is already running, - * it will be returned and the file argument will be ignored. + * a stream described by the given transport properties. If a reader task + * for the contact is already running, it will be returned and the + * transport properties will be ignored. */ - RemovableDriveTask startReaderTask(ContactId c, File f); + RemovableDriveTask startReaderTask(ContactId c, TransportProperties p); /** * Starts and returns a writer task for the given contact, writing to - * the given file. If a writer task for the contact is already running, - * it will be returned and the file argument will be ignored. + * a stream described by the given transport properties. If a writer task + * for the contact is already running, it will be returned and the + * transport properties will be ignored. */ - RemovableDriveTask startWriterTask(ContactId c, File f); + RemovableDriveTask startWriterTask(ContactId c, TransportProperties p); } diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java index 5388dab31..e27413a04 100644 --- a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/file/RemovableDriveTask.java @@ -2,16 +2,16 @@ package org.briarproject.bramble.api.plugin.file; import org.briarproject.bramble.api.Consumer; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; - -import java.io.File; +import org.briarproject.bramble.api.properties.TransportProperties; @NotNullByDefault public interface RemovableDriveTask extends Runnable { /** - * Returns the file that this task is reading from or writing to. + * Returns the {@link TransportProperties} that were used for creating + * this task. */ - File getFile(); + TransportProperties getTransportProperties(); /** * Adds an observer to the task. The observer will be notified of state @@ -37,10 +37,19 @@ public interface RemovableDriveTask extends Runnable { this.success = success; } + /** + * Returns the total length in bytes of the messages read or written + * so far. + */ public long getDone() { return done; } + /** + * Returns the total length in bytes of the messages that will have + * been read or written when the task is complete, or zero if the + * total is unknown. + */ public long getTotal() { return total; } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveManagerImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveManagerImpl.java index 3752449fa..262b33a69 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveManagerImpl.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveManagerImpl.java @@ -5,8 +5,8 @@ import org.briarproject.bramble.api.lifecycle.IoExecutor; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.plugin.file.RemovableDriveManager; import org.briarproject.bramble.api.plugin.file.RemovableDriveTask; +import org.briarproject.bramble.api.properties.TransportProperties; -import java.io.File; import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.Executor; @@ -46,8 +46,9 @@ class RemovableDriveManagerImpl } @Override - public RemovableDriveTask startReaderTask(ContactId c, File f) { - RemovableDriveTask task = taskFactory.createReader(this, c, f); + public RemovableDriveTask startReaderTask(ContactId c, + TransportProperties p) { + RemovableDriveTask task = taskFactory.createReader(this, c, p); RemovableDriveTask old = readers.putIfAbsent(c, task); if (old == null) { ioExecutor.execute(task); @@ -58,8 +59,9 @@ class RemovableDriveManagerImpl } @Override - public RemovableDriveTask startWriterTask(ContactId c, File f) { - RemovableDriveTask task = taskFactory.createWriter(this, c, f); + public RemovableDriveTask startWriterTask(ContactId c, + TransportProperties p) { + RemovableDriveTask task = taskFactory.createWriter(this, c, p); RemovableDriveTask old = writers.putIfAbsent(c, task); if (old == null) { ioExecutor.execute(task); diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveReaderTask.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveReaderTask.java index cc93c9099..5e5b270af 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveReaderTask.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveReaderTask.java @@ -8,9 +8,9 @@ import org.briarproject.bramble.api.event.EventListener; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.plugin.PluginManager; import org.briarproject.bramble.api.plugin.TransportConnectionReader; +import org.briarproject.bramble.api.properties.TransportProperties; import org.briarproject.bramble.api.sync.event.MessageAddedEvent; -import java.io.File; import java.io.IOException; import java.io.InputStream; import java.util.concurrent.Executor; @@ -33,22 +33,21 @@ class RemovableDriveReaderTask extends RemovableDriveTaskImpl EventBus eventBus, RemovableDriveTaskRegistry registry, ContactId contactId, - File file) { + TransportProperties transportProperties) { super(eventExecutor, pluginManager, connectionManager, eventBus, - registry, contactId, file); + registry, contactId, transportProperties); } @Override public void run() { TransportConnectionReader r = - getPlugin().createReader(createProperties()); + getPlugin().createReader(transportProperties); if (r == null) { LOG.warning("Failed to create reader"); registry.removeReader(contactId, this); setSuccess(false); return; } - setTotal(file.length()); eventBus.addListener(this); connectionManager.manageIncomingConnection(ID, new DecoratedReader(r)); } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactory.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactory.java index a81f88249..e90019d76 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactory.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactory.java @@ -3,15 +3,14 @@ package org.briarproject.bramble.plugin.file; import org.briarproject.bramble.api.contact.ContactId; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.plugin.file.RemovableDriveTask; - -import java.io.File; +import org.briarproject.bramble.api.properties.TransportProperties; @NotNullByDefault interface RemovableDriveTaskFactory { RemovableDriveTask createReader(RemovableDriveTaskRegistry registry, - ContactId c, File f); + ContactId c, TransportProperties p); RemovableDriveTask createWriter(RemovableDriveTaskRegistry registry, - ContactId c, File f); + ContactId c, TransportProperties p); } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java index dbf4b3bc7..b493054a0 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskFactoryImpl.java @@ -8,8 +8,8 @@ import org.briarproject.bramble.api.event.EventExecutor; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.plugin.PluginManager; import org.briarproject.bramble.api.plugin.file.RemovableDriveTask; +import org.briarproject.bramble.api.properties.TransportProperties; -import java.io.File; import java.util.concurrent.Executor; import javax.annotation.concurrent.Immutable; @@ -41,15 +41,15 @@ class RemovableDriveTaskFactoryImpl implements RemovableDriveTaskFactory { @Override public RemovableDriveTask createReader(RemovableDriveTaskRegistry registry, - ContactId c, File f) { + ContactId c, TransportProperties p) { return new RemovableDriveReaderTask(eventExecutor, pluginManager, - connectionManager, eventBus, registry, c, f); + connectionManager, eventBus, registry, c, p); } @Override public RemovableDriveTask createWriter(RemovableDriveTaskRegistry registry, - ContactId c, File f) { + ContactId c, TransportProperties p) { return new RemovableDriveWriterTask(db, eventExecutor, pluginManager, - connectionManager, eventBus, registry, c, f); + connectionManager, eventBus, registry, c, p); } } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java index de792f644..442d716e0 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveTaskImpl.java @@ -10,7 +10,6 @@ import org.briarproject.bramble.api.plugin.file.RemovableDriveTask; import org.briarproject.bramble.api.plugin.simplex.SimplexPlugin; import org.briarproject.bramble.api.properties.TransportProperties; -import java.io.File; import java.util.ArrayList; import java.util.List; import java.util.concurrent.Executor; @@ -20,7 +19,6 @@ import javax.annotation.concurrent.ThreadSafe; import static java.lang.Math.min; import static org.briarproject.bramble.api.nullsafety.NullSafety.requireNonNull; -import static org.briarproject.bramble.api.plugin.file.FileConstants.PROP_PATH; import static org.briarproject.bramble.api.plugin.file.RemovableDriveConstants.ID; @ThreadSafe @@ -33,7 +31,7 @@ abstract class RemovableDriveTaskImpl implements RemovableDriveTask { final EventBus eventBus; final RemovableDriveTaskRegistry registry; final ContactId contactId; - final File file; + final TransportProperties transportProperties; private final Object lock = new Object(); @GuardedBy("lock") @@ -48,19 +46,19 @@ abstract class RemovableDriveTaskImpl implements RemovableDriveTask { EventBus eventBus, RemovableDriveTaskRegistry registry, ContactId contactId, - File file) { + TransportProperties transportProperties) { this.eventExecutor = eventExecutor; this.pluginManager = pluginManager; this.connectionManager = connectionManager; this.eventBus = eventBus; this.registry = registry; this.contactId = contactId; - this.file = file; + this.transportProperties = transportProperties; } @Override - public File getFile() { - return file; + public TransportProperties getTransportProperties() { + return transportProperties; } @Override @@ -86,12 +84,6 @@ abstract class RemovableDriveTaskImpl implements RemovableDriveTask { return (SimplexPlugin) requireNonNull(pluginManager.getPlugin(ID)); } - TransportProperties createProperties() { - TransportProperties p = new TransportProperties(); - p.put(PROP_PATH, file.getAbsolutePath()); - return p; - } - void setTotal(long total) { synchronized (lock) { state = new State(state.getDone(), total, state.isFinished(), diff --git a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java index d9a9ed75c..7d2539557 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/plugin/file/RemovableDriveWriterTask.java @@ -11,9 +11,9 @@ import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.plugin.PluginManager; import org.briarproject.bramble.api.plugin.TransportConnectionWriter; import org.briarproject.bramble.api.plugin.simplex.SimplexPlugin; +import org.briarproject.bramble.api.properties.TransportProperties; import org.briarproject.bramble.api.sync.event.MessagesSentEvent; -import java.io.File; import java.io.IOException; import java.io.OutputStream; import java.util.concurrent.Executor; @@ -42,16 +42,16 @@ class RemovableDriveWriterTask extends RemovableDriveTaskImpl EventBus eventBus, RemovableDriveTaskRegistry registry, ContactId contactId, - File file) { + TransportProperties transportProperties) { super(eventExecutor, pluginManager, connectionManager, eventBus, - registry, contactId, file); + registry, contactId, transportProperties); this.db = db; } @Override public void run() { SimplexPlugin plugin = getPlugin(); - TransportConnectionWriter w = plugin.createWriter(createProperties()); + TransportConnectionWriter w = plugin.createWriter(transportProperties); if (w == null) { LOG.warning("Failed to create writer"); registry.removeWriter(contactId, this); diff --git a/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTest.java b/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTest.java index 56a40bcbe..ab3fa731f 100644 --- a/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTest.java +++ b/bramble-core/src/test/java/org/briarproject/bramble/plugin/file/RemovableDriveIntegrationTest.java @@ -11,6 +11,7 @@ import org.briarproject.bramble.api.identity.IdentityManager; import org.briarproject.bramble.api.lifecycle.LifecycleManager; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.plugin.file.RemovableDriveTask; +import org.briarproject.bramble.api.properties.TransportProperties; import org.briarproject.bramble.api.sync.event.MessageStateChangedEvent; import org.briarproject.bramble.test.BrambleTestCase; import org.briarproject.bramble.test.TestDatabaseConfigModule; @@ -22,6 +23,7 @@ import java.io.File; import java.util.concurrent.CountDownLatch; import static java.util.concurrent.TimeUnit.MILLISECONDS; +import static org.briarproject.bramble.api.plugin.file.FileConstants.PROP_PATH; import static org.briarproject.bramble.api.sync.validation.MessageState.DELIVERED; import static org.briarproject.bramble.test.TestUtils.deleteTestDirectory; import static org.briarproject.bramble.test.TestUtils.getSecretKey; @@ -96,8 +98,10 @@ public class RemovableDriveIntegrationTest extends BrambleTestCase { new MessageDeliveryListener(deliveries); device.getEventBus().addListener(listener); // Read the incoming stream + TransportProperties p = new TransportProperties(); + p.put(PROP_PATH, file.getAbsolutePath()); RemovableDriveTask reader = device.getRemovableDriveManager() - .startReaderTask(contactId, file); + .startReaderTask(contactId, p); CountDownLatch disposedLatch = new CountDownLatch(1); reader.addObserver(state -> { if (state.isFinished()) disposedLatch.countDown(); @@ -114,8 +118,10 @@ public class RemovableDriveIntegrationTest extends BrambleTestCase { ContactId contactId) throws Exception { // Write the outgoing stream to a file File file = File.createTempFile("sync", ".tmp", testDir); + TransportProperties p = new TransportProperties(); + p.put(PROP_PATH, file.getAbsolutePath()); RemovableDriveTask writer = device.getRemovableDriveManager() - .startWriterTask(contactId, file); + .startWriterTask(contactId, p); CountDownLatch disposedLatch = new CountDownLatch(1); writer.addObserver(state -> { if (state.isFinished()) disposedLatch.countDown();