Commit 86f65050 authored by Torsten Grote's avatar Torsten Grote

Re-introduce InvitationResponse

This was done, so private responses don't need to include a Nameable already.
Retreiving a nameable is tricky and requires a data migration,
so we just don't do it now.
parent d430b4fd
......@@ -21,11 +21,11 @@ import org.briarproject.briar.android.controller.ActivityLifecycleController;
import org.briarproject.briar.android.controller.handler.ResultExceptionHandler;
import org.briarproject.briar.api.android.AndroidNotificationManager;
import org.briarproject.briar.api.blog.Blog;
import org.briarproject.briar.api.blog.BlogInvitationResponse;
import org.briarproject.briar.api.blog.BlogManager;
import org.briarproject.briar.api.blog.BlogSharingManager;
import org.briarproject.briar.api.blog.event.BlogInvitationResponseReceivedEvent;
import org.briarproject.briar.api.blog.event.BlogPostAddedEvent;
import org.briarproject.briar.api.messaging.PrivateResponse;
import org.briarproject.briar.api.sharing.event.ContactLeftShareableEvent;
import java.util.ArrayList;
......@@ -107,8 +107,8 @@ class BlogControllerImpl extends BaseControllerImpl
} else if (e instanceof BlogInvitationResponseReceivedEvent) {
BlogInvitationResponseReceivedEvent b =
(BlogInvitationResponseReceivedEvent) e;
PrivateResponse<Blog> r = b.getMessageHeader();
if (r.getNameable().getId().equals(groupId) && r.wasAccepted()) {
BlogInvitationResponse r = b.getMessageHeader();
if (r.getShareableId().equals(groupId) && r.wasAccepted()) {
LOG.info("Blog invitation accepted");
onBlogInvitationAccepted(b.getContactId());
}
......
......@@ -167,14 +167,14 @@ abstract class ConversationItem {
if (ir.wasAccepted()) {
text = ctx.getString(
R.string.introduction_response_accepted_sent,
ir.getNameable().getName());
ir.getIntroducedAuthor().getName());
text += "\n\n" + ctx.getString(
R.string.introduction_response_accepted_sent_info,
ir.getNameable().getName());
ir.getIntroducedAuthor().getName());
} else {
text = ctx.getString(
R.string.introduction_response_declined_sent,
ir.getNameable().getName());
ir.getIntroducedAuthor().getName());
}
return new ConversationNoticeOutItem(ir.getId(), ir.getGroupId(),
text, null, ir.getTimestamp(), ir.isSent(), ir.isSeen());
......@@ -191,7 +191,7 @@ abstract class ConversationItem {
}
}
String text =
ctx.getString(res, contactName, ir.getNameable().getName());
ctx.getString(res, contactName, ir.getIntroducedAuthor().getName());
return new ConversationNoticeInItem(ir.getId(), ir.getGroupId(),
text, null, ir.getTimestamp(), ir.isRead());
}
......
......@@ -85,7 +85,7 @@ class ForumControllerImpl extends
ForumInvitationResponseReceivedEvent f =
(ForumInvitationResponseReceivedEvent) e;
ForumInvitationResponse r = f.getMessageHeader();
if (r.getNameable().getId().equals(getGroupId()) && r.wasAccepted()) {
if (r.getShareableId().equals(getGroupId()) && r.wasAccepted()) {
LOG.info("Forum invitation was accepted");
onForumInvitationAccepted(f.getContactId());
}
......
......@@ -100,7 +100,7 @@ class GroupControllerImpl extends
GroupInvitationResponseReceivedEvent g =
(GroupInvitationResponseReceivedEvent) e;
GroupInvitationResponse r = g.getMessageHeader();
if (getGroupId().equals(r.getNameable().getId()) && r.wasAccepted()) {
if (getGroupId().equals(r.getShareableId()) && r.wasAccepted()) {
listener.runOnUiThreadUnlessDestroyed(
() -> listener.onInvitationAccepted(g.getContactId()));
}
......
......@@ -4,16 +4,16 @@ import org.briarproject.bramble.api.nullsafety.NotNullByDefault;
import org.briarproject.bramble.api.sync.GroupId;
import org.briarproject.bramble.api.sync.MessageId;
import org.briarproject.briar.api.client.SessionId;
import org.briarproject.briar.api.messaging.PrivateResponse;
import org.briarproject.briar.api.sharing.InvitationResponse;
@NotNullByDefault
public class BlogInvitationResponse extends PrivateResponse<Blog> {
public class BlogInvitationResponse extends InvitationResponse {
public BlogInvitationResponse(MessageId id, GroupId groupId, long time,
boolean local, boolean sent, boolean seen, boolean read,
SessionId sessionId, Blog blog, boolean accept) {
super(id, groupId, time, local, sent, seen, read, sessionId, blog,
accept);
SessionId sessionId, boolean accept, GroupId shareableId) {
super(id, groupId, time, local, sent, seen, read, sessionId,
accept, shareableId);
}
}
......@@ -4,19 +4,19 @@ import org.briarproject.bramble.api.nullsafety.NotNullByDefault;
import org.briarproject.bramble.api.sync.GroupId;
import org.briarproject.bramble.api.sync.MessageId;
import org.briarproject.briar.api.client.SessionId;
import org.briarproject.briar.api.messaging.PrivateResponse;
import org.briarproject.briar.api.sharing.InvitationResponse;
import javax.annotation.concurrent.Immutable;
@Immutable
@NotNullByDefault
public class ForumInvitationResponse extends PrivateResponse<Forum> {
public class ForumInvitationResponse extends InvitationResponse {
public ForumInvitationResponse(MessageId id, GroupId groupId, long time,
boolean local, boolean sent, boolean seen, boolean read,
SessionId sessionId, Forum forum, boolean accept) {
super(id, groupId, time, local, sent, seen, read, sessionId, forum,
accept);
SessionId sessionId, boolean accept, GroupId shareableId) {
super(id, groupId, time, local, sent, seen, read, sessionId,
accept, shareableId);
}
}
......@@ -13,18 +13,24 @@ import static org.briarproject.briar.api.introduction.Role.INTRODUCER;
@Immutable
@NotNullByDefault
public class IntroductionResponse extends PrivateResponse<Author> {
public class IntroductionResponse extends PrivateResponse {
private final Author introducedAuthor;
private final Role ourRole;
public IntroductionResponse(MessageId messageId, GroupId groupId, long time,
boolean local, boolean sent, boolean seen, boolean read,
SessionId sessionId, Author author, boolean accepted, Role role) {
SessionId sessionId, boolean accepted, Author author, Role role) {
super(messageId, groupId, time, local, sent, seen, read, sessionId,
author, accepted);
accepted);
this.introducedAuthor = author;
this.ourRole = role;
}
public Author getIntroducedAuthor() {
return introducedAuthor;
}
public boolean isIntroducer() {
return ourRole == INTRODUCER;
}
......
package org.briarproject.briar.api.messaging;
import org.briarproject.bramble.api.Nameable;
import org.briarproject.bramble.api.nullsafety.NotNullByDefault;
import org.briarproject.bramble.api.sync.GroupId;
import org.briarproject.bramble.api.sync.MessageId;
......@@ -10,19 +9,16 @@ import javax.annotation.concurrent.Immutable;
@Immutable
@NotNullByDefault
public abstract class PrivateResponse<N extends Nameable>
extends PrivateMessageHeader {
public abstract class PrivateResponse extends PrivateMessageHeader {
private final SessionId sessionId;
private final N nameable;
private final boolean accepted;
public PrivateResponse(MessageId id, GroupId groupId, long time,
boolean local, boolean sent, boolean seen, boolean read,
SessionId sessionId, N nameable, boolean accepted) {
SessionId sessionId, boolean accepted) {
super(id, groupId, time, local, sent, seen, read);
this.sessionId = sessionId;
this.nameable = nameable;
this.accepted = accepted;
}
......@@ -30,10 +26,6 @@ public abstract class PrivateResponse<N extends Nameable>
return sessionId;
}
public N getNameable() {
return nameable;
}
public boolean wasAccepted() {
return accepted;
}
......
......@@ -4,20 +4,19 @@ import org.briarproject.bramble.api.nullsafety.NotNullByDefault;
import org.briarproject.bramble.api.sync.GroupId;
import org.briarproject.bramble.api.sync.MessageId;
import org.briarproject.briar.api.client.SessionId;
import org.briarproject.briar.api.messaging.PrivateResponse;
import org.briarproject.briar.api.privategroup.PrivateGroup;
import org.briarproject.briar.api.sharing.InvitationResponse;
import javax.annotation.concurrent.Immutable;
@Immutable
@NotNullByDefault
public class GroupInvitationResponse extends PrivateResponse<PrivateGroup> {
public class GroupInvitationResponse extends InvitationResponse {
public GroupInvitationResponse(MessageId id, GroupId groupId, long time,
boolean local, boolean sent, boolean seen, boolean read,
SessionId sessionId, PrivateGroup privateGroup, boolean accept) {
SessionId sessionId, boolean accept, GroupId shareableId) {
super(id, groupId, time, local, sent, seen, read, sessionId,
privateGroup, accept);
accept, shareableId);
}
}
package org.briarproject.briar.api.sharing;
import org.briarproject.bramble.api.sync.GroupId;
import org.briarproject.bramble.api.sync.MessageId;
import org.briarproject.briar.api.client.SessionId;
import org.briarproject.briar.api.messaging.PrivateResponse;
public abstract class InvitationResponse extends PrivateResponse {
private final GroupId shareableId;
public InvitationResponse(MessageId id, GroupId groupId, long time,
boolean local, boolean sent, boolean seen, boolean read,
SessionId sessionId, boolean accepted, GroupId shareableId) {
super(id, groupId, time, local, sent, seen, read, sessionId, accepted);
this.shareableId = shareableId;
}
public GroupId getShareableId() {
return shareableId;
}
}
......@@ -152,8 +152,8 @@ abstract class AbstractProtocolEngine<S extends Session>
IntroductionResponse response =
new IntroductionResponse(m.getMessageId(), m.getGroupId(),
m.getTimestamp(), false, false, false, false,
s.getSessionId(), otherAuthor,
m instanceof AcceptMessage, s.getRole());
s.getSessionId(), m instanceof AcceptMessage,
otherAuthor, s.getRole());
IntroductionResponseReceivedEvent e =
new IntroductionResponseReceivedEvent(response, c.getId());
txn.attach(e);
......
......@@ -495,7 +495,7 @@ class IntroductionManagerImpl extends ConversationClientImpl
} else throw new AssertionError();
return new IntroductionResponse(m, contactGroupId, meta.getTimestamp(),
meta.isLocal(), status.isSent(), status.isSeen(), meta.isRead(),
sessionId, author, accept, role);
sessionId, accept, author, role);
}
private void removeSessionWithIntroducer(Transaction txn,
......
......@@ -15,7 +15,6 @@ import org.briarproject.briar.api.client.MessageTracker;
import org.briarproject.briar.api.client.ProtocolStateException;
import org.briarproject.briar.api.client.SessionId;
import org.briarproject.briar.api.privategroup.GroupMessageFactory;
import org.briarproject.briar.api.privategroup.PrivateGroup;
import org.briarproject.briar.api.privategroup.PrivateGroupFactory;
import org.briarproject.briar.api.privategroup.PrivateGroupManager;
import org.briarproject.briar.api.privategroup.event.GroupInvitationResponseReceivedEvent;
......@@ -193,10 +192,8 @@ class CreatorProtocolEngine extends AbstractProtocolEngine<CreatorSession> {
setPrivateGroupVisibility(txn, s, SHARED);
// Broadcast an event
ContactId contactId = getContactId(txn, m.getContactGroupId());
PrivateGroup privateGroup =
privateGroupManager.getPrivateGroup(txn, m.getPrivateGroupId());
txn.attach(new GroupInvitationResponseReceivedEvent(
createInvitationResponse(m, privateGroup, true), contactId));
createInvitationResponse(m, true), contactId));
// Move to the JOINED state
return new CreatorSession(s.getContactGroupId(), s.getPrivateGroupId(),
sent.getId(), m.getId(), sent.getTimestamp(),
......@@ -217,10 +214,8 @@ class CreatorProtocolEngine extends AbstractProtocolEngine<CreatorSession> {
m.getTimestamp(), false);
// Broadcast an event
ContactId contactId = getContactId(txn, m.getContactGroupId());
PrivateGroup privateGroup =
privateGroupManager.getPrivateGroup(txn, m.getPrivateGroupId());
txn.attach(new GroupInvitationResponseReceivedEvent(
createInvitationResponse(m, privateGroup, false), contactId));
createInvitationResponse(m, false), contactId));
// Move to the START state
return new CreatorSession(s.getContactGroupId(), s.getPrivateGroupId(),
s.getLastLocalMessageId(), m.getId(), s.getLocalTimestamp(),
......@@ -258,11 +253,10 @@ class CreatorProtocolEngine extends AbstractProtocolEngine<CreatorSession> {
}
private GroupInvitationResponse createInvitationResponse(
GroupInvitationMessage m, PrivateGroup privateGroup,
boolean accept) {
GroupInvitationMessage m, boolean accept) {
SessionId sessionId = new SessionId(m.getPrivateGroupId().getBytes());
return new GroupInvitationResponse(m.getId(), m.getContactGroupId(),
m.getTimestamp(), false, false, true, false, sessionId,
privateGroup, accept);
accept, m.getPrivateGroupId());
}
}
......@@ -378,36 +378,21 @@ class GroupInvitationManagerImpl extends ConversationClientImpl
.getMessageMetadataAsDictionary(txn, contactGroupId, query);
List<PrivateMessageHeader> messages =
new ArrayList<>(results.size());
// get invite message first and remember private groups
Map<SessionId, PrivateGroup> privateGroups = new HashMap<>();
for (Entry<MessageId, BdfDictionary> e : results.entrySet()) {
MessageId m = e.getKey();
MessageMetadata meta =
messageParser.parseMetadata(e.getValue());
MessageType type = meta.getMessageType();
if (type != INVITE) continue;
MessageStatus status = db.getMessageStatus(txn, c, m);
GroupInvitationRequest invite = parseInvitationRequest(txn,
contactGroupId, m, meta, status);
messages.add(invite);
privateGroups.put(invite.getSessionId(), invite.getNameable());
}
for (Entry<MessageId, BdfDictionary> e : results.entrySet()) {
MessageId m = e.getKey();
MessageMetadata meta =
messageParser.parseMetadata(e.getValue());
MessageType type = meta.getMessageType();
if (type == INVITE) continue;
MessageStatus status = db.getMessageStatus(txn, c, m);
SessionId sessionId = getSessionId(meta.getPrivateGroupId());
PrivateGroup privateGroup = privateGroups.get(sessionId);
if (privateGroup == null) throw new AssertionError();
if (type == JOIN) {
if (type == INVITE) {
messages.add(parseInvitationRequest(txn, contactGroupId, m,
meta, status));
} else if (type == JOIN) {
messages.add(parseInvitationResponse(contactGroupId, m,
meta, status, sessionId, privateGroup, true));
meta, status, true));
} else if (type == LEAVE) {
messages.add(parseInvitationResponse(contactGroupId, m,
meta, status, sessionId, privateGroup, false));
meta, status, false));
}
}
return messages;
......@@ -436,12 +421,13 @@ class GroupInvitationManagerImpl extends ConversationClientImpl
private GroupInvitationResponse parseInvitationResponse(
GroupId contactGroupId, MessageId m, MessageMetadata meta,
MessageStatus status, SessionId sessionId,
PrivateGroup privateGroup, boolean accept) {
MessageStatus status, boolean accept) {
SessionId sessionId = getSessionId(meta.getPrivateGroupId());
return new GroupInvitationResponse(m, contactGroupId,
meta.getTimestamp(), meta.isLocal(), status.isSent(),
status.isSeen(), meta.isRead(), sessionId, privateGroup,
accept);
status.isSeen(), meta.isRead(), sessionId, accept,
meta.getPrivateGroupId()
);
}
@Override
......
......@@ -30,10 +30,10 @@ public class BlogInvitationFactoryImpl
@Override
public BlogInvitationResponse createInvitationResponse(MessageId id,
GroupId contactGroupId, long time, boolean local, boolean sent,
boolean seen, boolean read, Blog blog, boolean accept) {
SessionId sessionId = new SessionId(blog.getId().getBytes());
boolean seen, boolean read, boolean accept, GroupId shareableId) {
SessionId sessionId = new SessionId(shareableId.getBytes());
return new BlogInvitationResponse(id, contactGroupId, time, local, sent,
seen, read, sessionId, blog, accept);
seen, read, sessionId, accept, shareableId);
}
}
......@@ -58,21 +58,21 @@ class BlogProtocolEngineImpl extends ProtocolEngineImpl<Blog> {
@Override
Event getInvitationResponseReceivedEvent(AcceptMessage m,
ContactId contactId, Blog shareable) {
ContactId contactId) {
BlogInvitationResponse response = invitationFactory
.createInvitationResponse(m.getId(), m.getContactGroupId(),
m.getTimestamp(), false, false, true, false,
shareable, true);
true, m.getShareableId());
return new BlogInvitationResponseReceivedEvent(response, contactId);
}
@Override
Event getInvitationResponseReceivedEvent(DeclineMessage m,
ContactId contactId, Blog shareable) {
ContactId contactId) {
BlogInvitationResponse response = invitationFactory
.createInvitationResponse(m.getId(), m.getContactGroupId(),
m.getTimestamp(), false, false, true, false,
shareable, true);
true, m.getShareableId());
return new BlogInvitationResponseReceivedEvent(response, contactId);
}
......
......@@ -30,10 +30,10 @@ public class ForumInvitationFactoryImpl
@Override
public ForumInvitationResponse createInvitationResponse(MessageId id,
GroupId contactGroupId, long time, boolean local, boolean sent,
boolean seen, boolean read, Forum forum, boolean accept) {
SessionId sessionId = new SessionId(forum.getId().getBytes());
boolean seen, boolean read, boolean accept, GroupId shareableId) {
SessionId sessionId = new SessionId(shareableId.getBytes());
return new ForumInvitationResponse(id, contactGroupId, time, local,
sent, seen, read, sessionId, forum, accept);
sent, seen, read, sessionId, accept, shareableId);
}
}
......@@ -31,8 +31,7 @@ import static org.briarproject.briar.api.forum.ForumManager.MAJOR_VERSION;
class ForumProtocolEngineImpl extends ProtocolEngineImpl<Forum> {
private final ForumManager forumManager;
private final InvitationFactory<Forum, ForumInvitationResponse>
invitationFactory;
private final InvitationFactory<Forum, ForumInvitationResponse> invitationFactory;
@Inject
ForumProtocolEngineImpl(DatabaseComponent db,
......@@ -60,21 +59,21 @@ class ForumProtocolEngineImpl extends ProtocolEngineImpl<Forum> {
@Override
Event getInvitationResponseReceivedEvent(AcceptMessage m,
ContactId contactId, Forum shareable) {
ContactId contactId) {
ForumInvitationResponse response = invitationFactory
.createInvitationResponse(m.getId(), m.getContactGroupId(),
m.getTimestamp(), false, false, true, false,
shareable, true);
true, m.getShareableId());
return new ForumInvitationResponseReceivedEvent(response, contactId);
}
@Override
Event getInvitationResponseReceivedEvent(DeclineMessage m,
ContactId contactId, Forum shareable) {
ContactId contactId) {
ForumInvitationResponse response = invitationFactory
.createInvitationResponse(m.getId(), m.getContactGroupId(),
m.getTimestamp(), false, false, true, false,
shareable, true);
true, m.getShareableId());
return new ForumInvitationResponseReceivedEvent(response, contactId);
}
......
......@@ -4,17 +4,17 @@ import org.briarproject.bramble.api.contact.ContactId;
import org.briarproject.bramble.api.sync.GroupId;
import org.briarproject.bramble.api.sync.MessageId;
import org.briarproject.briar.api.messaging.PrivateRequest;
import org.briarproject.briar.api.messaging.PrivateResponse;
import org.briarproject.briar.api.sharing.InvitationResponse;
import org.briarproject.briar.api.sharing.Shareable;
public interface InvitationFactory<S extends Shareable, I extends PrivateResponse<S>> {
public interface InvitationFactory<S extends Shareable, R extends InvitationResponse> {
PrivateRequest<S> createInvitationRequest(boolean local, boolean sent,
boolean seen, boolean read, InviteMessage<S> m, ContactId c,
boolean available, boolean canBeOpened);
I createInvitationResponse(MessageId id,
GroupId contactGroupId, long time, boolean local, boolean sent,
boolean seen, boolean read, S shareable, boolean accept);
R createInvitationResponse(MessageId id, GroupId contactGroupId, long time,
boolean local, boolean sent, boolean seen, boolean read,
boolean accept, GroupId shareableId);
}
......@@ -113,7 +113,13 @@ abstract class ProtocolEngineImpl<S extends Shareable>
private Message sendInviteMessage(Transaction txn, Session s,
@Nullable String message, long timestamp) throws DbException {
BdfList descriptor = getDescriptor(txn, s.getShareableId());
Group g = db.getGroup(txn, s.getShareableId());
BdfList descriptor;
try {
descriptor = clientHelper.toList(g.getDescriptor());
} catch (FormatException e) {
throw new DbException(e); // Invalid group descriptor
}
long localTimestamp = Math.max(timestamp, getLocalTimestamp(s));
Message m = messageEncoder.encodeInviteMessage(s.getContactGroupId(),
localTimestamp, s.getLastLocalMessageId(), descriptor, message);
......@@ -287,7 +293,7 @@ abstract class ProtocolEngineImpl<S extends Shareable>
if (m.getTimestamp() <= s.getInviteTimestamp())
return abortWithMessage(txn, s);
// The dependency, if any, must be the last remote message
if (!isValidDependency(s, m.getPreviousMessageId()))
if (isInvalidDependency(s, m.getPreviousMessageId()))
return abortWithMessage(txn, s);
// Mark the invite message visible in the UI and (un)available to answer
markMessageVisibleInUi(txn, m.getId());
......@@ -311,7 +317,7 @@ abstract class ProtocolEngineImpl<S extends Shareable>
if (m.getTimestamp() <= s.getInviteTimestamp())
return abortWithMessage(txn, s);
// The dependency, if any, must be the last remote message
if (!isValidDependency(s, m.getPreviousMessageId()))
if (isInvalidDependency(s, m.getPreviousMessageId()))
return abortWithMessage(txn, s);
// Mark the invite message visible in the UI and unavailable to answer
markMessageVisibleInUi(txn, m.getId());
......@@ -358,7 +364,7 @@ abstract class ProtocolEngineImpl<S extends Shareable>
if (m.getTimestamp() <= s.getInviteTimestamp())
return abortWithMessage(txn, s);
// The dependency, if any, must be the last remote message
if (!isValidDependency(s, m.getPreviousMessageId()))
if (isInvalidDependency(s, m.getPreviousMessageId()))
return abortWithMessage(txn, s);
// Mark the response visible in the UI
markMessageVisibleInUi(txn, m.getId());
......@@ -367,8 +373,7 @@ abstract class ProtocolEngineImpl<S extends Shareable>
m.getTimestamp(), false);
// Broadcast an event
ContactId contactId = getContactId(txn, m.getContactGroupId());
S shareable = getShareable(txn, s.getShareableId());
txn.attach(getInvitationResponseReceivedEvent(m, contactId, shareable));
txn.attach(getInvitationResponseReceivedEvent(m, contactId));
// Move to the next state
return new Session(nextState, s.getContactGroupId(), s.getShareableId(),
s.getLastLocalMessageId(), m.getId(), s.getLocalTimestamp(),
......@@ -386,7 +391,7 @@ abstract class ProtocolEngineImpl<S extends Shareable>
}
abstract Event getInvitationResponseReceivedEvent(AcceptMessage m,
ContactId contactId, S shareable);
ContactId contactId);
@Override
public Session onDeclineMessage(Transaction txn, Session s,
......@@ -411,7 +416,7 @@ abstract class ProtocolEngineImpl<S extends Shareable>
if (m.getTimestamp() <= s.getInviteTimestamp())
return abortWithMessage(txn, s);
// The dependency, if any, must be the last remote message
if (!isValidDependency(s, m.getPreviousMessageId()))
if (isInvalidDependency(s, m.getPreviousMessageId()))
return abortWithMessage(txn, s);
// Mark the response visible in the UI
markMessageVisibleInUi(txn, m.getId());
......@@ -426,8 +431,7 @@ abstract class ProtocolEngineImpl<S extends Shareable>
}
// Broadcast an event
ContactId contactId = getContactId(txn, m.getContactGroupId());
S shareable = getShareable(txn, s.getShareableId());
txn.attach(getInvitationResponseReceivedEvent(m, contactId, shareable));
txn.attach(getInvitationResponseReceivedEvent(m, contactId));
// Move to the next state
return new Session(START, s.getContactGroupId(), s.getShareableId(),
s.getLastLocalMessageId(), m.getId(), s.getLocalTimestamp(),
......@@ -435,7 +439,7 @@ abstract class ProtocolEngineImpl<S extends Shareable>
}
abstract Event getInvitationResponseReceivedEvent(DeclineMessage m,
ContactId contactId, S shareable);
ContactId contactId);
@Override
public Session onLeaveMessage(Transaction txn, Session s,
......@@ -459,7 +463,7 @@ abstract class ProtocolEngineImpl<S extends Shareable>
private Session onRemoteLeaveWhenInvited(Transaction txn, Session s,
LeaveMessage m) throws DbException, FormatException {
// The dependency, if any, must be the last remote message
if (!isValidDependency(s, m.getPreviousMessageId()))
if (isInvalidDependency(s, m.getPreviousMessageId()))
return abortWithMessage(txn, s);
// Mark any invite messages in the session unavailable to answer
markInvitesUnavailableToAnswer(txn, s);
......@@ -472,7 +476,7 @@ abstract class ProtocolEngineImpl<S extends Shareable>
private Session onRemoteLeaveWhenLocalLeft(Transaction txn, Session s,
LeaveMessage m) throws DbException, FormatException {
// The dependency, if any, must be the last remote message
if (!isValidDependency(s, m.getPreviousMessageId()))
if (isInvalidDependency(s, m.getPreviousMessageId()))
return abortWithMessage(txn, s);
// Move to the next state
return new Session(START, s.getContactGroupId(), s.getShareableId(),
......@@ -483,7 +487,7 @@ abstract class ProtocolEngineImpl<S extends Shareable>
private Session onRemoteLeaveWhenSharing(Transaction txn, Session s,
LeaveMessage m) throws DbException, FormatException {
// The dependency, if any, must be the last remote message
if (!isValidDependency(s, m.getPreviousMessageId()))
if (isInvalidDependency(s, m.getPreviousMessageId()))
return abortWithMessage(txn, s);
// Broadcast event informing that contact left
ContactId contactId = getContactId(txn, s.getContactGroupId());
......@@ -526,26 +530,6 @@ abstract class ProtocolEngineImpl<S extends Shareable>
sent.getId(), null, 0, 0);
}
private S getShareable(Transaction txn, GroupId groupId)
throws DbException {
BdfList descriptor = getDescriptor(txn, groupId);
try {
return messageParser.createShareable(descriptor);
} catch (FormatException e) {
throw new DbException(e);
}
}
private BdfList getDescriptor(Transaction txn, GroupId groupId)
throws DbException {
Group g = db.getGroup(txn, groupId);
try {
return clientHelper.toList(g.getDescriptor());
} catch (FormatException e) {
throw new DbException(e); // Invalid group descriptor
}
}
private void markInvitesUnavailableToAnswer(Transaction txn, Session s)
throws DbException, FormatException {
GroupId shareableId = s.getShareableId();
......@@ -639,11 +623,11 @@ abstract class ProtocolEngineImpl<S extends Shareable>
return new ContactId(meta.getLong(GROUP_KEY_CONTACT_ID).intValue());
}
private boolean isValidDependency(Session session,
private boolean isInvalidDependency(Session session,
@Nullable MessageId dependency) {
MessageId expected = session.getLastRemoteMessageId();
if (dependency == null) return expected == null;
return expected != null && dependency.equals(expected);
if (dependency == null) return expected != null;
return expected == null || !dependency.equals(expected);
}
private long getLocalTimestamp(Session session) {
......
......@@ -28,7 +28,7 @@ import org.briarproject.briar.api.client.MessageTracker;
import org.briarproject.briar.api.client.SessionId;
import org.briarproject.briar.api.messaging.PrivateMessageHeader;
import org.briarproject.briar.api.messaging.PrivateRequest;
import org.briarproject.briar.api.messaging.PrivateResponse;
import org.briarproject.briar.api.sharing.InvitationResponse;
import org.briarproject.briar.api.sharing.Shareable;
import org.briarproject.briar.api.sharing.SharingInvitationItem;
import org.briarproject.briar.api.sharing.SharingManager;
......