From 3c128ce9f838eefb940c35bb219ef5c93a5f05c9 Mon Sep 17 00:00:00 2001 From: Mikhail Lopatkin Date: Mon, 1 Jan 2024 18:15:45 +0100 Subject: [PATCH] Handle app closing in AdbDataSource As device listeners are now also ui-thread-confined, there is no need in ThreadSafeObservable anymore. Without the async disconnect notifications, the AdbDataSource properly handles device list shutdown. Issue: fixes #332 --- .../mlopatkin/andlogview/device/Device.java | 4 ++-- .../andlogview/device/DeviceImpl.java | 24 ++++++++++++------- .../andlogview/device/FakeDevice.java | 8 +++---- .../liblogcat/ddmlib/AdbDataSource.java | 5 ++-- .../ui/device/AdbDataSourceFactory.java | 11 ++------- 5 files changed, 26 insertions(+), 26 deletions(-) diff --git a/device/src/main/java/name/mlopatkin/andlogview/device/Device.java b/device/src/main/java/name/mlopatkin/andlogview/device/Device.java index fa825278..b31a3aac 100644 --- a/device/src/main/java/name/mlopatkin/andlogview/device/Device.java +++ b/device/src/main/java/name/mlopatkin/andlogview/device/Device.java @@ -16,7 +16,7 @@ package name.mlopatkin.andlogview.device; -import name.mlopatkin.andlogview.utils.events.ThreadSafeObservable; +import name.mlopatkin.andlogview.utils.events.Observable; import java.util.Arrays; import java.util.List; @@ -68,5 +68,5 @@ default Command command(String... commandLine) { * * @return the observable */ - ThreadSafeObservable asObservable(); + Observable asObservable(); } diff --git a/device/src/main/java/name/mlopatkin/andlogview/device/DeviceImpl.java b/device/src/main/java/name/mlopatkin/andlogview/device/DeviceImpl.java index c40a1449..7dc29f72 100644 --- a/device/src/main/java/name/mlopatkin/andlogview/device/DeviceImpl.java +++ b/device/src/main/java/name/mlopatkin/andlogview/device/DeviceImpl.java @@ -16,8 +16,8 @@ package name.mlopatkin.andlogview.device; -import name.mlopatkin.andlogview.utils.events.ThreadSafeObservable; -import name.mlopatkin.andlogview.utils.events.ThreadSafeSubject; +import name.mlopatkin.andlogview.utils.events.Observable; +import name.mlopatkin.andlogview.utils.events.Subject; import java.util.List; @@ -25,7 +25,7 @@ class DeviceImpl implements DeviceInternal { private final DeviceKey deviceKey; private final LoggingDevice device; private final DeviceProperties deviceProperties; - private final ThreadSafeSubject observers = new ThreadSafeSubject<>(); + private final Subject observers = new Subject<>(); public DeviceImpl(DeviceKey deviceKey, LoggingDevice device, DeviceProperties deviceProperties) { this.deviceKey = deviceKey; @@ -86,27 +86,35 @@ public Command command(List commandLine) { } @Override - public ThreadSafeObservable asObservable() { + public Observable asObservable() { return observers.asObservable(); } @Override public void notifyProvisioned() { - observers.forEach(obs -> obs.onDeviceConnected(this)); + for (var obs : observers) { + obs.onDeviceConnected(this); + } } @Override public void notifyChanged() { - observers.forEach(obs -> obs.onDeviceChanged(this)); + for (var obs : observers) { + obs.onDeviceChanged(this); + } } @Override public void notifyConnected() { - observers.forEach(obs -> obs.onProvisionalDeviceConnected(this)); + for (var obs : observers) { + obs.onProvisionalDeviceConnected(this); + } } @Override public void notifyDisconnected() { - observers.forEach(obs -> obs.onDeviceDisconnected(this)); + for (var obs : observers) { + obs.onDeviceDisconnected(this); + } } } diff --git a/device/src/testFixtures/java/name/mlopatkin/andlogview/device/FakeDevice.java b/device/src/testFixtures/java/name/mlopatkin/andlogview/device/FakeDevice.java index 2eb45a0b..5db0668c 100644 --- a/device/src/testFixtures/java/name/mlopatkin/andlogview/device/FakeDevice.java +++ b/device/src/testFixtures/java/name/mlopatkin/andlogview/device/FakeDevice.java @@ -18,8 +18,8 @@ import name.mlopatkin.andlogview.test.StrictMock; import name.mlopatkin.andlogview.thirdparty.device.AndroidVersionCodes; -import name.mlopatkin.andlogview.utils.events.ThreadSafeObservable; -import name.mlopatkin.andlogview.utils.events.ThreadSafeSubject; +import name.mlopatkin.andlogview.utils.events.Observable; +import name.mlopatkin.andlogview.utils.events.Subject; import com.android.ddmlib.IDevice; @@ -88,9 +88,9 @@ public Command command(List commandLine) { } @Override - public ThreadSafeObservable asObservable() { + public Observable asObservable() { // TODO(mlopatkin) implement it? - return new ThreadSafeSubject().asObservable(); + return new Subject().asObservable(); } protected FakeCommand onCommand(List commandLine) { diff --git a/src/name/mlopatkin/andlogview/liblogcat/ddmlib/AdbDataSource.java b/src/name/mlopatkin/andlogview/liblogcat/ddmlib/AdbDataSource.java index 50e2292d..3955cebd 100644 --- a/src/name/mlopatkin/andlogview/liblogcat/ddmlib/AdbDataSource.java +++ b/src/name/mlopatkin/andlogview/liblogcat/ddmlib/AdbDataSource.java @@ -36,7 +36,6 @@ import java.util.HashSet; import java.util.Map; import java.util.Set; -import java.util.concurrent.Executor; public class AdbDataSource implements DataSource, BufferReceiver { /** @@ -78,7 +77,7 @@ default void onDataSourceClosed() {} private @Nullable RecordListener listener; private boolean closed = false; - public AdbDataSource(Device device, Executor uiExecutor) { + public AdbDataSource(Device device) { assert device != null; assert device.isOnline(); this.device = device; @@ -101,7 +100,7 @@ public void onDeviceChanged(Device device) { invalidateAndClose(InvalidationReason.OFFLINE); } } - }, uiExecutor); + }); } @Override diff --git a/src/name/mlopatkin/andlogview/ui/device/AdbDataSourceFactory.java b/src/name/mlopatkin/andlogview/ui/device/AdbDataSourceFactory.java index 28f2dfe4..36bc47ce 100644 --- a/src/name/mlopatkin/andlogview/ui/device/AdbDataSourceFactory.java +++ b/src/name/mlopatkin/andlogview/ui/device/AdbDataSourceFactory.java @@ -16,29 +16,22 @@ package name.mlopatkin.andlogview.ui.device; -import name.mlopatkin.andlogview.AppExecutors; import name.mlopatkin.andlogview.device.Device; import name.mlopatkin.andlogview.liblogcat.ddmlib.AdbDataSource; import name.mlopatkin.andlogview.liblogcat.ddmlib.DeviceDisconnectedHandler; import org.checkerframework.checker.nullness.qual.Nullable; -import java.util.concurrent.Executor; import java.util.function.Consumer; import javax.inject.Inject; -import javax.inject.Named; public class AdbDataSourceFactory { private final DeviceDisconnectedHandler deviceDisconnectedHandler; - private final Executor uiExecutor; @Inject - AdbDataSourceFactory( - DeviceDisconnectedHandler deviceDisconnectedHandler, - @Named(AppExecutors.UI_EXECUTOR) Executor uiExecutor) { + AdbDataSourceFactory(DeviceDisconnectedHandler deviceDisconnectedHandler) { this.deviceDisconnectedHandler = deviceDisconnectedHandler; - this.uiExecutor = uiExecutor; } public void selectDeviceAndOpenAsDataSource( @@ -54,7 +47,7 @@ public void selectDeviceAndOpenAsDataSource( } public void openDeviceAsDataSource(Device device, Consumer callback) { - AdbDataSource dataSource = new AdbDataSource(device, uiExecutor); + AdbDataSource dataSource = new AdbDataSource(device); deviceDisconnectedHandler.startWatching(dataSource); callback.accept(dataSource); }