Broadcast events after committing transactions.

This commit is contained in:
akwizgran
2016-02-11 14:49:41 +00:00
parent de8cc50fb4
commit 146dac056d
6 changed files with 88 additions and 85 deletions

View File

@@ -49,9 +49,9 @@ public interface DatabaseComponent {
Transaction startTransaction() throws DbException; Transaction startTransaction() throws DbException;
/** /**
* Ends a transaction. If the transaction's * Ends a transaction. If the transaction is marked as complete, the
* {@link Transaction#setComplete() commit} flag is set, the * transaction is committed and any events attached to the transaction are
* transaction is committed, otherwise it is aborted. * broadcast; otherwise the transaction is aborted.
*/ */
void endTransaction(Transaction txn) throws DbException; void endTransaction(Transaction txn) throws DbException;

View File

@@ -1,11 +1,19 @@
package org.briarproject.api.db; package org.briarproject.api.db;
import org.briarproject.api.event.Event;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
/** /**
* A wrapper around a database transaction. Transactions are not thread-safe. * A wrapper around a database transaction. Transactions are not thread-safe.
*/ */
public class Transaction { public class Transaction {
private final Object txn; private final Object txn;
private List<Event> events = null;
private boolean complete = false; private boolean complete = false;
public Transaction(Object txn) { public Transaction(Object txn) {
@@ -20,6 +28,23 @@ public class Transaction {
return txn; return txn;
} }
/**
* Attaches an event to be broadcast when the transaction has been
* committed.
*/
public void attach(Event e) {
if (events == null) events = new ArrayList<Event>();
events.add(e);
}
/**
* Returns any events attached to the transaction.
*/
public List<Event> getEvents() {
if (events == null) return Collections.emptyList();
return events;
}
/** /**
* Returns true if the transaction is ready to be committed. * Returns true if the transaction is ready to be committed.
*/ */

View File

@@ -9,9 +9,6 @@ import org.briarproject.api.db.DatabaseComponent;
import org.briarproject.api.db.DbException; import org.briarproject.api.db.DbException;
import org.briarproject.api.db.NoSuchContactException; import org.briarproject.api.db.NoSuchContactException;
import org.briarproject.api.db.Transaction; import org.briarproject.api.db.Transaction;
import org.briarproject.api.event.ContactAddedEvent;
import org.briarproject.api.event.ContactRemovedEvent;
import org.briarproject.api.event.EventBus;
import org.briarproject.api.identity.Author; import org.briarproject.api.identity.Author;
import org.briarproject.api.identity.AuthorId; import org.briarproject.api.identity.AuthorId;
import org.briarproject.api.identity.IdentityManager.RemoveIdentityHook; import org.briarproject.api.identity.IdentityManager.RemoveIdentityHook;
@@ -37,14 +34,12 @@ class ContactManagerImpl implements ContactManager, Service,
Logger.getLogger(ContactManagerImpl.class.getName()); Logger.getLogger(ContactManagerImpl.class.getName());
private final DatabaseComponent db; private final DatabaseComponent db;
private final EventBus eventBus;
private final List<AddContactHook> addHooks; private final List<AddContactHook> addHooks;
private final List<RemoveContactHook> removeHooks; private final List<RemoveContactHook> removeHooks;
@Inject @Inject
ContactManagerImpl(DatabaseComponent db, EventBus eventBus) { ContactManagerImpl(DatabaseComponent db) {
this.db = db; this.db = db;
this.eventBus = eventBus;
addHooks = new CopyOnWriteArrayList<AddContactHook>(); addHooks = new CopyOnWriteArrayList<AddContactHook>();
removeHooks = new CopyOnWriteArrayList<RemoveContactHook>(); removeHooks = new CopyOnWriteArrayList<RemoveContactHook>();
} }
@@ -53,8 +48,6 @@ class ContactManagerImpl implements ContactManager, Service,
public boolean start() { public boolean start() {
// Finish adding/removing any partly added/removed contacts // Finish adding/removing any partly added/removed contacts
try { try {
List<ContactId> added = new ArrayList<ContactId>();
List<ContactId> removed = new ArrayList<ContactId>();
Transaction txn = db.startTransaction(); Transaction txn = db.startTransaction();
try { try {
for (Contact c : db.getContacts(txn)) { for (Contact c : db.getContacts(txn)) {
@@ -62,22 +55,16 @@ class ContactManagerImpl implements ContactManager, Service,
for (AddContactHook hook : addHooks) for (AddContactHook hook : addHooks)
hook.addingContact(txn, c); hook.addingContact(txn, c);
db.setContactStatus(txn, c.getId(), ACTIVE); db.setContactStatus(txn, c.getId(), ACTIVE);
added.add(c.getId());
} else if (c.getStatus().equals(REMOVING)) { } else if (c.getStatus().equals(REMOVING)) {
for (RemoveContactHook hook : removeHooks) for (RemoveContactHook hook : removeHooks)
hook.removingContact(txn, c); hook.removingContact(txn, c);
db.removeContact(txn, c.getId()); db.removeContact(txn, c.getId());
removed.add(c.getId());
} }
} }
txn.setComplete(); txn.setComplete();
} finally { } finally {
db.endTransaction(txn); db.endTransaction(txn);
} }
for (ContactId c : added)
eventBus.broadcast(new ContactAddedEvent(c));
for (ContactId c : removed)
eventBus.broadcast(new ContactRemovedEvent(c));
return true; return true;
} catch (DbException e) { } catch (DbException e) {
if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e);
@@ -115,7 +102,6 @@ class ContactManagerImpl implements ContactManager, Service,
} finally { } finally {
db.endTransaction(txn); db.endTransaction(txn);
} }
eventBus.broadcast(new ContactAddedEvent(c));
return c; return c;
} }
@@ -159,7 +145,6 @@ class ContactManagerImpl implements ContactManager, Service,
} finally { } finally {
db.endTransaction(txn); db.endTransaction(txn);
} }
eventBus.broadcast(new ContactRemovedEvent(c));
} }
private void removeContact(Transaction txn, ContactId c) private void removeContact(Transaction txn, ContactId c)

View File

@@ -15,10 +15,15 @@ import org.briarproject.api.db.NoSuchMessageException;
import org.briarproject.api.db.NoSuchTransportException; import org.briarproject.api.db.NoSuchTransportException;
import org.briarproject.api.db.StorageStatus; import org.briarproject.api.db.StorageStatus;
import org.briarproject.api.db.Transaction; import org.briarproject.api.db.Transaction;
import org.briarproject.api.event.ContactAddedEvent;
import org.briarproject.api.event.ContactRemovedEvent;
import org.briarproject.api.event.Event;
import org.briarproject.api.event.EventBus; import org.briarproject.api.event.EventBus;
import org.briarproject.api.event.GroupAddedEvent; import org.briarproject.api.event.GroupAddedEvent;
import org.briarproject.api.event.GroupRemovedEvent; import org.briarproject.api.event.GroupRemovedEvent;
import org.briarproject.api.event.GroupVisibilityUpdatedEvent; import org.briarproject.api.event.GroupVisibilityUpdatedEvent;
import org.briarproject.api.event.LocalAuthorAddedEvent;
import org.briarproject.api.event.LocalAuthorRemovedEvent;
import org.briarproject.api.event.MessageAddedEvent; import org.briarproject.api.event.MessageAddedEvent;
import org.briarproject.api.event.MessageRequestedEvent; import org.briarproject.api.event.MessageRequestedEvent;
import org.briarproject.api.event.MessageSharedEvent; import org.briarproject.api.event.MessageSharedEvent;
@@ -66,8 +71,6 @@ import static org.briarproject.api.sync.ValidationManager.Validity.UNKNOWN;
import static org.briarproject.api.sync.ValidationManager.Validity.VALID; import static org.briarproject.api.sync.ValidationManager.Validity.VALID;
import static org.briarproject.db.DatabaseConstants.MAX_OFFERED_MESSAGES; import static org.briarproject.db.DatabaseConstants.MAX_OFFERED_MESSAGES;
// TODO: Callers should broadcast events after committing transactions
/** /**
* An implementation of DatabaseComponent using reentrant read-write locks. * An implementation of DatabaseComponent using reentrant read-write locks.
* Depending on the JVM's lock implementation, this implementation may allow * Depending on the JVM's lock implementation, this implementation may allow
@@ -127,8 +130,12 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
public void endTransaction(Transaction transaction) throws DbException { public void endTransaction(Transaction transaction) throws DbException {
T txn = txnClass.cast(transaction.unbox()); T txn = txnClass.cast(transaction.unbox());
if (transaction.isComplete()) db.commitTransaction(txn); if (transaction.isComplete()) {
else db.abortTransaction(txn); db.commitTransaction(txn);
for (Event e : transaction.getEvents()) eventBus.broadcast(e);
} else {
db.abortTransaction(txn);
}
} }
private T unbox(Transaction transaction) { private T unbox(Transaction transaction) {
@@ -143,42 +150,40 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
throw new NoSuchLocalAuthorException(); throw new NoSuchLocalAuthorException();
if (db.containsContact(txn, remote.getId(), local)) if (db.containsContact(txn, remote.getId(), local))
throw new ContactExistsException(); throw new ContactExistsException();
return db.addContact(txn, remote, local); ContactId c = db.addContact(txn, remote, local);
transaction.attach(new ContactAddedEvent(c));
return c;
} }
public void addGroup(Transaction transaction, Group g) throws DbException { public void addGroup(Transaction transaction, Group g) throws DbException {
boolean added = false;
T txn = unbox(transaction); T txn = unbox(transaction);
if (!db.containsGroup(txn, g.getId())) { if (!db.containsGroup(txn, g.getId())) {
db.addGroup(txn, g); db.addGroup(txn, g);
added = true; transaction.attach(new GroupAddedEvent(g));
} }
if (added) eventBus.broadcast(new GroupAddedEvent(g));
} }
public void addLocalAuthor(Transaction transaction, LocalAuthor a) public void addLocalAuthor(Transaction transaction, LocalAuthor a)
throws DbException { throws DbException {
T txn = unbox(transaction); T txn = unbox(transaction);
if (!db.containsLocalAuthor(txn, a.getId())) if (!db.containsLocalAuthor(txn, a.getId())) {
db.addLocalAuthor(txn, a); db.addLocalAuthor(txn, a);
transaction.attach(new LocalAuthorAddedEvent(a.getId()));
}
} }
public void addLocalMessage(Transaction transaction, Message m, ClientId c, public void addLocalMessage(Transaction transaction, Message m, ClientId c,
Metadata meta, boolean shared) throws DbException { Metadata meta, boolean shared) throws DbException {
boolean added = false;
T txn = unbox(transaction); T txn = unbox(transaction);
if (!db.containsGroup(txn, m.getGroupId())) if (!db.containsGroup(txn, m.getGroupId()))
throw new NoSuchGroupException(); throw new NoSuchGroupException();
if (!db.containsMessage(txn, m.getId())) { if (!db.containsMessage(txn, m.getId())) {
addMessage(txn, m, VALID, shared, null); addMessage(txn, m, VALID, shared, null);
added = true; transaction.attach(new MessageAddedEvent(m, null));
transaction.attach(new MessageValidatedEvent(m, c, true, true));
if (shared) transaction.attach(new MessageSharedEvent(m));
} }
db.mergeMessageMetadata(txn, m.getId(), meta); db.mergeMessageMetadata(txn, m.getId(), meta);
if (added) {
eventBus.broadcast(new MessageAddedEvent(m, null));
eventBus.broadcast(new MessageValidatedEvent(m, c, true, true));
if (shared) eventBus.broadcast(new MessageSharedEvent(m));
}
} }
/** /**
@@ -206,13 +211,11 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
public void addTransport(Transaction transaction, TransportId t, public void addTransport(Transaction transaction, TransportId t,
int maxLatency) throws DbException { int maxLatency) throws DbException {
boolean added = false;
T txn = unbox(transaction); T txn = unbox(transaction);
if (!db.containsTransport(txn, t)) { if (!db.containsTransport(txn, t)) {
db.addTransport(txn, t, maxLatency); db.addTransport(txn, t, maxLatency);
added = true; transaction.attach(new TransportAddedEvent(t, maxLatency));
} }
if (added) eventBus.broadcast(new TransportAddedEvent(t, maxLatency));
} }
public void addTransportKeys(Transaction transaction, ContactId c, public void addTransportKeys(Transaction transaction, ContactId c,
@@ -266,9 +269,9 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
messages.add(db.getRawMessage(txn, m)); messages.add(db.getRawMessage(txn, m));
db.updateExpiryTime(txn, c, m, maxLatency); db.updateExpiryTime(txn, c, m, maxLatency);
} }
if (!ids.isEmpty()) db.lowerRequestedFlag(txn, c, ids); if (ids.isEmpty()) return null;
if (messages.isEmpty()) return null; db.lowerRequestedFlag(txn, c, ids);
if (!ids.isEmpty()) eventBus.broadcast(new MessagesSentEvent(c, ids)); transaction.attach(new MessagesSentEvent(c, ids));
return Collections.unmodifiableList(messages); return Collections.unmodifiableList(messages);
} }
@@ -309,9 +312,9 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
messages.add(db.getRawMessage(txn, m)); messages.add(db.getRawMessage(txn, m));
db.updateExpiryTime(txn, c, m, maxLatency); db.updateExpiryTime(txn, c, m, maxLatency);
} }
if (!ids.isEmpty()) db.lowerRequestedFlag(txn, c, ids); if (ids.isEmpty()) return null;
if (messages.isEmpty()) return null; db.lowerRequestedFlag(txn, c, ids);
if (!ids.isEmpty()) eventBus.broadcast(new MessagesSentEvent(c, ids)); transaction.attach(new MessagesSentEvent(c, ids));
return Collections.unmodifiableList(messages); return Collections.unmodifiableList(messages);
} }
@@ -486,7 +489,6 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
public void mergeSettings(Transaction transaction, Settings s, public void mergeSettings(Transaction transaction, Settings s,
String namespace) throws DbException { String namespace) throws DbException {
boolean changed = false;
T txn = unbox(transaction); T txn = unbox(transaction);
Settings old = db.getSettings(txn, namespace); Settings old = db.getSettings(txn, namespace);
Settings merged = new Settings(); Settings merged = new Settings();
@@ -494,9 +496,8 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
merged.putAll(s); merged.putAll(s);
if (!merged.equals(old)) { if (!merged.equals(old)) {
db.mergeSettings(txn, s, namespace); db.mergeSettings(txn, s, namespace);
changed = true; transaction.attach(new SettingsUpdatedEvent(namespace));
} }
if (changed) eventBus.broadcast(new SettingsUpdatedEvent(namespace));
} }
public void receiveAck(Transaction transaction, ContactId c, Ack a) public void receiveAck(Transaction transaction, ContactId c, Ack a)
@@ -511,24 +512,21 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
acked.add(m); acked.add(m);
} }
} }
eventBus.broadcast(new MessagesAckedEvent(c, acked)); transaction.attach(new MessagesAckedEvent(c, acked));
} }
public void receiveMessage(Transaction transaction, ContactId c, Message m) public void receiveMessage(Transaction transaction, ContactId c, Message m)
throws DbException { throws DbException {
boolean duplicate, visible;
T txn = unbox(transaction); T txn = unbox(transaction);
if (!db.containsContact(txn, c)) if (!db.containsContact(txn, c))
throw new NoSuchContactException(); throw new NoSuchContactException();
duplicate = db.containsMessage(txn, m.getId()); if (db.containsVisibleGroup(txn, c, m.getGroupId())) {
visible = db.containsVisibleGroup(txn, c, m.getGroupId()); if (!db.containsMessage(txn, m.getId())) {
if (visible) { addMessage(txn, m, UNKNOWN, false, c);
if (!duplicate) addMessage(txn, m, UNKNOWN, false, c); transaction.attach(new MessageAddedEvent(m, c));
}
db.raiseAckFlag(txn, c, m.getId()); db.raiseAckFlag(txn, c, m.getId());
} transaction.attach(new MessageToAckEvent(c));
if (visible) {
if (!duplicate) eventBus.broadcast(new MessageAddedEvent(m, c));
eventBus.broadcast(new MessageToAckEvent(c));
} }
} }
@@ -550,8 +548,8 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
count++; count++;
} }
} }
if (ack) eventBus.broadcast(new MessageToAckEvent(c)); if (ack) transaction.attach(new MessageToAckEvent(c));
if (request) eventBus.broadcast(new MessageToRequestEvent(c)); if (request) transaction.attach(new MessageToRequestEvent(c));
} }
public void receiveRequest(Transaction transaction, ContactId c, Request r) public void receiveRequest(Transaction transaction, ContactId c, Request r)
@@ -567,7 +565,7 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
requested = true; requested = true;
} }
} }
if (requested) eventBus.broadcast(new MessageRequestedEvent(c)); if (requested) transaction.attach(new MessageRequestedEvent(c));
} }
public void removeContact(Transaction transaction, ContactId c) public void removeContact(Transaction transaction, ContactId c)
@@ -576,6 +574,7 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
if (!db.containsContact(txn, c)) if (!db.containsContact(txn, c))
throw new NoSuchContactException(); throw new NoSuchContactException();
db.removeContact(txn, c); db.removeContact(txn, c);
transaction.attach(new ContactRemovedEvent(c));
} }
public void removeGroup(Transaction transaction, Group g) public void removeGroup(Transaction transaction, Group g)
@@ -587,8 +586,8 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
throw new NoSuchGroupException(); throw new NoSuchGroupException();
affected = db.getVisibility(txn, id); affected = db.getVisibility(txn, id);
db.removeGroup(txn, id); db.removeGroup(txn, id);
eventBus.broadcast(new GroupRemovedEvent(g)); transaction.attach(new GroupRemovedEvent(g));
eventBus.broadcast(new GroupVisibilityUpdatedEvent(affected)); transaction.attach(new GroupVisibilityUpdatedEvent(affected));
} }
public void removeLocalAuthor(Transaction transaction, AuthorId a) public void removeLocalAuthor(Transaction transaction, AuthorId a)
@@ -597,6 +596,7 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
if (!db.containsLocalAuthor(txn, a)) if (!db.containsLocalAuthor(txn, a))
throw new NoSuchLocalAuthorException(); throw new NoSuchLocalAuthorException();
db.removeLocalAuthor(txn, a); db.removeLocalAuthor(txn, a);
transaction.attach(new LocalAuthorRemovedEvent(a));
} }
public void removeTransport(Transaction transaction, TransportId t) public void removeTransport(Transaction transaction, TransportId t)
@@ -605,7 +605,7 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
if (!db.containsTransport(txn, t)) if (!db.containsTransport(txn, t))
throw new NoSuchTransportException(); throw new NoSuchTransportException();
db.removeTransport(txn, t); db.removeTransport(txn, t);
eventBus.broadcast(new TransportRemovedEvent(t)); transaction.attach(new TransportRemovedEvent(t));
} }
public void setContactStatus(Transaction transaction, ContactId c, public void setContactStatus(Transaction transaction, ContactId c,
@@ -630,7 +630,7 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
if (!db.containsMessage(txn, m.getId())) if (!db.containsMessage(txn, m.getId()))
throw new NoSuchMessageException(); throw new NoSuchMessageException();
db.setMessageShared(txn, m.getId(), shared); db.setMessageShared(txn, m.getId(), shared);
if (shared) eventBus.broadcast(new MessageSharedEvent(m)); if (shared) transaction.attach(new MessageSharedEvent(m));
} }
public void setMessageValid(Transaction transaction, Message m, ClientId c, public void setMessageValid(Transaction transaction, Message m, ClientId c,
@@ -639,7 +639,7 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
if (!db.containsMessage(txn, m.getId())) if (!db.containsMessage(txn, m.getId()))
throw new NoSuchMessageException(); throw new NoSuchMessageException();
db.setMessageValid(txn, m.getId(), valid); db.setMessageValid(txn, m.getId(), valid);
eventBus.broadcast(new MessageValidatedEvent(m, c, false, valid)); transaction.attach(new MessageValidatedEvent(m, c, false, valid));
} }
public void setReorderingWindow(Transaction transaction, ContactId c, public void setReorderingWindow(Transaction transaction, ContactId c,
@@ -665,8 +665,8 @@ class DatabaseComponentImpl<T> implements DatabaseComponent {
if (visible && !wasVisible) db.addVisibility(txn, c, g); if (visible && !wasVisible) db.addVisibility(txn, c, g);
else if (!visible && wasVisible) db.removeVisibility(txn, c, g); else if (!visible && wasVisible) db.removeVisibility(txn, c, g);
if (visible != wasVisible) { if (visible != wasVisible) {
eventBus.broadcast(new GroupVisibilityUpdatedEvent( List<ContactId> affected = Collections.singletonList(c);
Collections.singletonList(c))); transaction.attach(new GroupVisibilityUpdatedEvent(affected));
} }
} }

View File

@@ -6,9 +6,6 @@ import org.briarproject.api.db.DatabaseComponent;
import org.briarproject.api.db.DbException; import org.briarproject.api.db.DbException;
import org.briarproject.api.db.NoSuchLocalAuthorException; import org.briarproject.api.db.NoSuchLocalAuthorException;
import org.briarproject.api.db.Transaction; import org.briarproject.api.db.Transaction;
import org.briarproject.api.event.EventBus;
import org.briarproject.api.event.LocalAuthorAddedEvent;
import org.briarproject.api.event.LocalAuthorRemovedEvent;
import org.briarproject.api.identity.AuthorId; import org.briarproject.api.identity.AuthorId;
import org.briarproject.api.identity.IdentityManager; import org.briarproject.api.identity.IdentityManager;
import org.briarproject.api.identity.LocalAuthor; import org.briarproject.api.identity.LocalAuthor;
@@ -32,14 +29,12 @@ class IdentityManagerImpl implements IdentityManager, Service {
Logger.getLogger(IdentityManagerImpl.class.getName()); Logger.getLogger(IdentityManagerImpl.class.getName());
private final DatabaseComponent db; private final DatabaseComponent db;
private final EventBus eventBus;
private final List<AddIdentityHook> addHooks; private final List<AddIdentityHook> addHooks;
private final List<RemoveIdentityHook> removeHooks; private final List<RemoveIdentityHook> removeHooks;
@Inject @Inject
IdentityManagerImpl(DatabaseComponent db, EventBus eventBus) { IdentityManagerImpl(DatabaseComponent db) {
this.db = db; this.db = db;
this.eventBus = eventBus;
addHooks = new CopyOnWriteArrayList<AddIdentityHook>(); addHooks = new CopyOnWriteArrayList<AddIdentityHook>();
removeHooks = new CopyOnWriteArrayList<RemoveIdentityHook>(); removeHooks = new CopyOnWriteArrayList<RemoveIdentityHook>();
} }
@@ -48,8 +43,6 @@ class IdentityManagerImpl implements IdentityManager, Service {
public boolean start() { public boolean start() {
// Finish adding/removing any partly added/removed pseudonyms // Finish adding/removing any partly added/removed pseudonyms
try { try {
List<AuthorId> added = new ArrayList<AuthorId>();
List<AuthorId> removed = new ArrayList<AuthorId>();
Transaction txn = db.startTransaction(); Transaction txn = db.startTransaction();
try { try {
for (LocalAuthor a : db.getLocalAuthors(txn)) { for (LocalAuthor a : db.getLocalAuthors(txn)) {
@@ -57,22 +50,16 @@ class IdentityManagerImpl implements IdentityManager, Service {
for (AddIdentityHook hook : addHooks) for (AddIdentityHook hook : addHooks)
hook.addingIdentity(txn, a); hook.addingIdentity(txn, a);
db.setLocalAuthorStatus(txn, a.getId(), ACTIVE); db.setLocalAuthorStatus(txn, a.getId(), ACTIVE);
added.add(a.getId());
} else if (a.getStatus().equals(REMOVING)) { } else if (a.getStatus().equals(REMOVING)) {
for (RemoveIdentityHook hook : removeHooks) for (RemoveIdentityHook hook : removeHooks)
hook.removingIdentity(txn, a); hook.removingIdentity(txn, a);
db.removeLocalAuthor(txn, a.getId()); db.removeLocalAuthor(txn, a.getId());
removed.add(a.getId());
} }
} }
txn.setComplete(); txn.setComplete();
} finally { } finally {
db.endTransaction(txn); db.endTransaction(txn);
} }
for (AuthorId a : added)
eventBus.broadcast(new LocalAuthorAddedEvent(a));
for (AuthorId a : removed)
eventBus.broadcast(new LocalAuthorRemovedEvent(a));
return true; return true;
} catch (DbException e) { } catch (DbException e) {
if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e);
@@ -107,7 +94,6 @@ class IdentityManagerImpl implements IdentityManager, Service {
} finally { } finally {
db.endTransaction(txn); db.endTransaction(txn);
} }
eventBus.broadcast(new LocalAuthorAddedEvent(localAuthor.getId()));
} }
@Override @Override
@@ -154,6 +140,5 @@ class IdentityManagerImpl implements IdentityManager, Service {
} finally { } finally {
db.endTransaction(txn); db.endTransaction(txn);
} }
eventBus.broadcast(new LocalAuthorRemovedEvent(a));
} }
} }

View File

@@ -15,10 +15,14 @@ import org.briarproject.api.db.NoSuchMessageException;
import org.briarproject.api.db.NoSuchTransportException; import org.briarproject.api.db.NoSuchTransportException;
import org.briarproject.api.db.StorageStatus; import org.briarproject.api.db.StorageStatus;
import org.briarproject.api.db.Transaction; import org.briarproject.api.db.Transaction;
import org.briarproject.api.event.ContactAddedEvent;
import org.briarproject.api.event.ContactRemovedEvent;
import org.briarproject.api.event.EventBus; import org.briarproject.api.event.EventBus;
import org.briarproject.api.event.GroupAddedEvent; import org.briarproject.api.event.GroupAddedEvent;
import org.briarproject.api.event.GroupRemovedEvent; import org.briarproject.api.event.GroupRemovedEvent;
import org.briarproject.api.event.GroupVisibilityUpdatedEvent; import org.briarproject.api.event.GroupVisibilityUpdatedEvent;
import org.briarproject.api.event.LocalAuthorAddedEvent;
import org.briarproject.api.event.LocalAuthorRemovedEvent;
import org.briarproject.api.event.MessageAddedEvent; import org.briarproject.api.event.MessageAddedEvent;
import org.briarproject.api.event.MessageRequestedEvent; import org.briarproject.api.event.MessageRequestedEvent;
import org.briarproject.api.event.MessageSharedEvent; import org.briarproject.api.event.MessageSharedEvent;
@@ -136,6 +140,7 @@ public class DatabaseComponentImplTest extends BriarTestCase {
oneOf(database).containsLocalAuthor(txn, localAuthorId); oneOf(database).containsLocalAuthor(txn, localAuthorId);
will(returnValue(false)); will(returnValue(false));
oneOf(database).addLocalAuthor(txn, localAuthor); oneOf(database).addLocalAuthor(txn, localAuthor);
oneOf(eventBus).broadcast(with(any(LocalAuthorAddedEvent.class)));
// addContact() // addContact()
oneOf(database).containsLocalAuthor(txn, localAuthorId); oneOf(database).containsLocalAuthor(txn, localAuthorId);
will(returnValue(true)); will(returnValue(true));
@@ -143,6 +148,7 @@ public class DatabaseComponentImplTest extends BriarTestCase {
will(returnValue(false)); will(returnValue(false));
oneOf(database).addContact(txn, author, localAuthorId); oneOf(database).addContact(txn, author, localAuthorId);
will(returnValue(contactId)); will(returnValue(contactId));
oneOf(eventBus).broadcast(with(any(ContactAddedEvent.class)));
// getContacts() // getContacts()
oneOf(database).getContacts(txn); oneOf(database).getContacts(txn);
will(returnValue(Collections.singletonList(contact))); will(returnValue(Collections.singletonList(contact)));
@@ -170,10 +176,12 @@ public class DatabaseComponentImplTest extends BriarTestCase {
oneOf(database).containsContact(txn, contactId); oneOf(database).containsContact(txn, contactId);
will(returnValue(true)); will(returnValue(true));
oneOf(database).removeContact(txn, contactId); oneOf(database).removeContact(txn, contactId);
oneOf(eventBus).broadcast(with(any(ContactRemovedEvent.class)));
// removeLocalAuthor() // removeLocalAuthor()
oneOf(database).containsLocalAuthor(txn, localAuthorId); oneOf(database).containsLocalAuthor(txn, localAuthorId);
will(returnValue(true)); will(returnValue(true));
oneOf(database).removeLocalAuthor(txn, localAuthorId); oneOf(database).removeLocalAuthor(txn, localAuthorId);
oneOf(eventBus).broadcast(with(any(LocalAuthorRemovedEvent.class)));
// endTransaction() // endTransaction()
oneOf(database).commitTransaction(txn); oneOf(database).commitTransaction(txn);
// close() // close()
@@ -743,6 +751,7 @@ public class DatabaseComponentImplTest extends BriarTestCase {
oneOf(database).containsLocalAuthor(txn, localAuthorId); oneOf(database).containsLocalAuthor(txn, localAuthorId);
will(returnValue(false)); will(returnValue(false));
oneOf(database).addLocalAuthor(txn, localAuthor); oneOf(database).addLocalAuthor(txn, localAuthor);
oneOf(eventBus).broadcast(with(any(LocalAuthorAddedEvent.class)));
// addContact() // addContact()
oneOf(database).containsLocalAuthor(txn, localAuthorId); oneOf(database).containsLocalAuthor(txn, localAuthorId);
will(returnValue(true)); will(returnValue(true));
@@ -750,6 +759,7 @@ public class DatabaseComponentImplTest extends BriarTestCase {
will(returnValue(false)); will(returnValue(false));
oneOf(database).addContact(txn, author, localAuthorId); oneOf(database).addContact(txn, author, localAuthorId);
will(returnValue(contactId)); will(returnValue(contactId));
oneOf(eventBus).broadcast(with(any(ContactAddedEvent.class)));
// endTransaction() // endTransaction()
oneOf(database).commitTransaction(txn); oneOf(database).commitTransaction(txn);
// Check whether the transport is in the DB (which it's not) // Check whether the transport is in the DB (which it's not)
@@ -1137,8 +1147,6 @@ public class DatabaseComponentImplTest extends BriarTestCase {
will(returnValue(txn)); will(returnValue(txn));
oneOf(database).containsContact(txn, contactId); oneOf(database).containsContact(txn, contactId);
will(returnValue(true)); will(returnValue(true));
oneOf(database).containsMessage(txn, messageId);
will(returnValue(false));
oneOf(database).containsVisibleGroup(txn, contactId, groupId); oneOf(database).containsVisibleGroup(txn, contactId, groupId);
will(returnValue(false)); will(returnValue(false));
oneOf(database).commitTransaction(txn); oneOf(database).commitTransaction(txn);