From fbe375cc4ef8618236c5050e4abe0b8efc3a1b79 Mon Sep 17 00:00:00 2001
From: Torsten Grote <t@grobox.de>
Date: Thu, 9 May 2019 11:43:22 -0300
Subject: [PATCH] Use event instead of CommitAction to handle removed
 PendingContacts

---
 .../bramble/api/contact/ContactManager.java   |  4 +--
 .../event/PendingContactRemovedEvent.java     | 26 +++++++++++++++++++
 .../bramble/contact/ContactManagerImpl.java   |  7 ++---
 .../android/contact/ContactListFragment.java  |  4 ++-
 .../remote/PendingContactListActivity.java    |  3 +--
 .../remote/PendingContactListViewModel.java   | 10 +++----
 .../add/remote/PendingContactViewHolder.java  |  7 +++--
 7 files changed, 45 insertions(+), 16 deletions(-)
 create mode 100644 bramble-api/src/main/java/org/briarproject/bramble/api/contact/event/PendingContactRemovedEvent.java

diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/contact/ContactManager.java b/bramble-api/src/main/java/org/briarproject/bramble/api/contact/ContactManager.java
index a11226bc63..5ae366c2e8 100644
--- a/bramble-api/src/main/java/org/briarproject/bramble/api/contact/ContactManager.java
+++ b/bramble-api/src/main/java/org/briarproject/bramble/api/contact/ContactManager.java
@@ -80,10 +80,8 @@ public interface ContactManager {
 	/**
 	 * Removes a {@link PendingContact} that is in state
 	 * {@link PendingContactState FAILED}.
-	 * @param commitAction an action to run on the main thread after removing.
 	 */
-	void removePendingContact(PendingContactId pendingContact,
-			Runnable commitAction) throws DbException;
+	void removePendingContact(PendingContactId pendingContact) throws DbException;
 
 	/**
 	 * Returns the contact with the given ID.
diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/contact/event/PendingContactRemovedEvent.java b/bramble-api/src/main/java/org/briarproject/bramble/api/contact/event/PendingContactRemovedEvent.java
new file mode 100644
index 0000000000..4d9c0e2815
--- /dev/null
+++ b/bramble-api/src/main/java/org/briarproject/bramble/api/contact/event/PendingContactRemovedEvent.java
@@ -0,0 +1,26 @@
+package org.briarproject.bramble.api.contact.event;
+
+import org.briarproject.bramble.api.contact.PendingContactId;
+import org.briarproject.bramble.api.event.Event;
+import org.briarproject.bramble.api.nullsafety.NotNullByDefault;
+
+import javax.annotation.concurrent.Immutable;
+
+/**
+ * An event that is broadcast when a pending contact is removed.
+ */
+@Immutable
+@NotNullByDefault
+public class PendingContactRemovedEvent extends Event {
+
+	private final PendingContactId id;
+
+	public PendingContactRemovedEvent(PendingContactId id) {
+		this.id = id;
+	}
+
+	public PendingContactId getId() {
+		return id;
+	}
+
+}
diff --git a/bramble-core/src/main/java/org/briarproject/bramble/contact/ContactManagerImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/contact/ContactManagerImpl.java
index 5f4912d993..7951069a44 100644
--- a/bramble-core/src/main/java/org/briarproject/bramble/contact/ContactManagerImpl.java
+++ b/bramble-core/src/main/java/org/briarproject/bramble/contact/ContactManagerImpl.java
@@ -6,6 +6,7 @@ import org.briarproject.bramble.api.contact.ContactManager;
 import org.briarproject.bramble.api.contact.PendingContact;
 import org.briarproject.bramble.api.contact.PendingContactId;
 import org.briarproject.bramble.api.contact.event.ContactAddedRemotelyEvent;
+import org.briarproject.bramble.api.contact.event.PendingContactRemovedEvent;
 import org.briarproject.bramble.api.contact.event.PendingContactStateChangedEvent;
 import org.briarproject.bramble.api.crypto.SecretKey;
 import org.briarproject.bramble.api.db.DatabaseComponent;
@@ -218,8 +219,7 @@ class ContactManagerImpl implements ContactManager {
 	}
 
 	@Override
-	public void removePendingContact(PendingContactId id,
-			Runnable commitAction) throws DbException {
+	public void removePendingContact(PendingContactId id) throws DbException {
 		// TODO replace with real implementation
 		for (PendingContact pc : pendingContacts) {
 			if (pc.getId().equals(id)) {
@@ -231,7 +231,8 @@ class ContactManagerImpl implements ContactManager {
 			Thread.sleep(250);
 		} catch (InterruptedException ignored) {
 		}
-		db.transaction(true, txn -> txn.attach(commitAction));
+		db.transaction(true,
+				txn -> txn.attach(new PendingContactRemovedEvent(id)));
 	}
 
 	@Override
diff --git a/briar-android/src/main/java/org/briarproject/briar/android/contact/ContactListFragment.java b/briar-android/src/main/java/org/briarproject/briar/android/contact/ContactListFragment.java
index df3efdea43..f1eaa533cc 100644
--- a/briar-android/src/main/java/org/briarproject/briar/android/contact/ContactListFragment.java
+++ b/briar-android/src/main/java/org/briarproject/briar/android/contact/ContactListFragment.java
@@ -20,6 +20,7 @@ import org.briarproject.bramble.api.contact.ContactManager;
 import org.briarproject.bramble.api.contact.event.ContactAddedEvent;
 import org.briarproject.bramble.api.contact.event.ContactAddedRemotelyEvent;
 import org.briarproject.bramble.api.contact.event.ContactRemovedEvent;
+import org.briarproject.bramble.api.contact.event.PendingContactRemovedEvent;
 import org.briarproject.bramble.api.contact.event.PendingContactStateChangedEvent;
 import org.briarproject.bramble.api.db.DbException;
 import org.briarproject.bramble.api.db.NoSuchContactException;
@@ -299,7 +300,8 @@ public class ContactListFragment extends BaseFragment implements EventListener,
 			if (pe.getPendingContactState() == WAITING_FOR_CONNECTION) {
 				checkForPendingContacts();
 			}
-		} else if (e instanceof ContactAddedRemotelyEvent) {
+		} else if (e instanceof PendingContactRemovedEvent ||
+				e instanceof ContactAddedRemotelyEvent) {
 			checkForPendingContacts();
 		}
 	}
diff --git a/briar-android/src/main/java/org/briarproject/briar/android/contact/add/remote/PendingContactListActivity.java b/briar-android/src/main/java/org/briarproject/briar/android/contact/add/remote/PendingContactListActivity.java
index b716222ee6..c731a70f98 100644
--- a/briar-android/src/main/java/org/briarproject/briar/android/contact/add/remote/PendingContactListActivity.java
+++ b/briar-android/src/main/java/org/briarproject/briar/android/contact/add/remote/PendingContactListActivity.java
@@ -86,8 +86,7 @@ public class PendingContactListActivity extends BriarActivity
 
 	@Override
 	public void onFailedPendingContactRemoved(PendingContact pendingContact) {
-		viewModel.removePendingContact(pendingContact.getId(),
-				() -> adapter.remove(pendingContact));
+		viewModel.removePendingContact(pendingContact.getId());
 	}
 
 	private void onPendingContactsChanged(Collection<PendingContact> contacts) {
diff --git a/briar-android/src/main/java/org/briarproject/briar/android/contact/add/remote/PendingContactListViewModel.java b/briar-android/src/main/java/org/briarproject/briar/android/contact/add/remote/PendingContactListViewModel.java
index c97e0538ba..c0772517f0 100644
--- a/briar-android/src/main/java/org/briarproject/briar/android/contact/add/remote/PendingContactListViewModel.java
+++ b/briar-android/src/main/java/org/briarproject/briar/android/contact/add/remote/PendingContactListViewModel.java
@@ -9,6 +9,7 @@ import org.briarproject.bramble.api.contact.ContactManager;
 import org.briarproject.bramble.api.contact.PendingContact;
 import org.briarproject.bramble.api.contact.PendingContactId;
 import org.briarproject.bramble.api.contact.event.ContactAddedRemotelyEvent;
+import org.briarproject.bramble.api.contact.event.PendingContactRemovedEvent;
 import org.briarproject.bramble.api.contact.event.PendingContactStateChangedEvent;
 import org.briarproject.bramble.api.db.DatabaseExecutor;
 import org.briarproject.bramble.api.db.DbException;
@@ -63,7 +64,8 @@ public class PendingContactListViewModel extends AndroidViewModel
 	@Override
 	public void eventOccurred(Event e) {
 		if (e instanceof ContactAddedRemotelyEvent ||
-				e instanceof PendingContactStateChangedEvent) {
+				e instanceof PendingContactStateChangedEvent ||
+				e instanceof PendingContactRemovedEvent) {
 			loadPendingContacts();
 		}
 	}
@@ -82,16 +84,14 @@ public class PendingContactListViewModel extends AndroidViewModel
 		return pendingContacts;
 	}
 
-	void removePendingContact(PendingContactId id, Runnable commitAction) {
+	void removePendingContact(PendingContactId id) {
 		dbExecutor.execute(() -> {
 			try {
-				contactManager
-						.removePendingContact(id, commitAction);
+				contactManager.removePendingContact(id);
 			} catch (DbException e) {
 				logException(LOG, WARNING, e);
 			}
 		});
-		loadPendingContacts();
 	}
 
 }
diff --git a/briar-android/src/main/java/org/briarproject/briar/android/contact/add/remote/PendingContactViewHolder.java b/briar-android/src/main/java/org/briarproject/briar/android/contact/add/remote/PendingContactViewHolder.java
index 1f0524f2f8..ac3b2a9177 100644
--- a/briar-android/src/main/java/org/briarproject/briar/android/contact/add/remote/PendingContactViewHolder.java
+++ b/briar-android/src/main/java/org/briarproject/briar/android/contact/add/remote/PendingContactViewHolder.java
@@ -40,8 +40,10 @@ class PendingContactViewHolder extends ViewHolder {
 		avatar.setBackgroundBytes(item.getId().getBytes());
 		name.setText(item.getAlias());
 		time.setText(formatDate(time.getContext(), item.getTimestamp()));
-		removeButton.setOnClickListener(
-				v -> listener.onFailedPendingContactRemoved(item));
+		removeButton.setOnClickListener(v -> {
+			listener.onFailedPendingContactRemoved(item);
+			removeButton.setEnabled(false);
+		});
 
 		int color = ContextCompat
 				.getColor(status.getContext(), R.color.briar_green);
@@ -69,6 +71,7 @@ class PendingContactViewHolder extends ViewHolder {
 		}
 		status.setTextColor(color);
 		removeButton.setVisibility(buttonVisibility);
+		removeButton.setEnabled(true);
 	}
 
 }
-- 
GitLab