Fix membership diffs that occur during a GV1->GV2 migration.

Co-authored-by: Alan Evans <alan@signal.org>
This commit is contained in:
Greyson Parrelli
2020-11-20 13:26:17 -05:00
committed by GitHub
parent 89f2c25d73
commit 4166e7931e
2 changed files with 24 additions and 2 deletions

View File

@@ -483,6 +483,11 @@ public final class GroupDatabase extends Database {
/** /**
* Migrates a V1 group to a V2 group. * Migrates a V1 group to a V2 group.
*
* @param decryptedGroup The state that represents the group on the server. This will be used to
* determine if we need to save our old membership list and stuff. It will
* *not* be stored as the definitive group state as-is. In order to ensure
* proper diffing, we modify this model to have our V1 membership.
*/ */
public @NonNull GroupId.V2 migrateToV2(@NonNull GroupId.V1 groupIdV1, @NonNull DecryptedGroup decryptedGroup) { public @NonNull GroupId.V2 migrateToV2(@NonNull GroupId.V1 groupIdV1, @NonNull DecryptedGroup decryptedGroup) {
SQLiteDatabase db = databaseHelper.getWritableDatabase(); SQLiteDatabase db = databaseHelper.getWritableDatabase();
@@ -513,7 +518,7 @@ public final class GroupDatabase extends Database {
DatabaseFactory.getRecipientDatabase(context).updateGroupId(groupIdV1, groupIdV2); DatabaseFactory.getRecipientDatabase(context).updateGroupId(groupIdV1, groupIdV2);
update(groupMasterKey, decryptedGroup); update(groupMasterKey, updateToHaveV1Membership(decryptedGroup, record.getMembers()));
db.setTransactionSuccessful(); db.setTransactionSuccessful();
} finally { } finally {
@@ -523,6 +528,23 @@ public final class GroupDatabase extends Database {
return groupIdV2; return groupIdV2;
} }
private static DecryptedGroup updateToHaveV1Membership(@NonNull DecryptedGroup serverGroup, @NonNull List<RecipientId> v1Members) {
DecryptedGroup.Builder builder = serverGroup.toBuilder();
builder.clearMembers();
for (RecipientId v1MemberId : v1Members) {
Recipient v1Member = Recipient.resolved(v1MemberId);
if (v1Member.hasUuid()) {
builder.addMembers(DecryptedMember.newBuilder()
.setUuid(UuidUtil.toByteString(v1Member.getUuid().get()))
.setRole(Member.Role.ADMINISTRATOR)
.build());
}
}
return builder.build();
}
public void update(@NonNull GroupMasterKey groupMasterKey, @NonNull DecryptedGroup decryptedGroup) { public void update(@NonNull GroupMasterKey groupMasterKey, @NonNull DecryptedGroup decryptedGroup) {
update(GroupId.v2(groupMasterKey), decryptedGroup); update(GroupId.v2(groupMasterKey), decryptedGroup);
} }

View File

@@ -197,7 +197,7 @@ public abstract class MessageRecord extends DisplayRecord {
DecryptedGroupV2Context decryptedGroupV2Context = DecryptedGroupV2Context.parseFrom(decoded); DecryptedGroupV2Context decryptedGroupV2Context = DecryptedGroupV2Context.parseFrom(decoded);
GroupsV2UpdateMessageProducer updateMessageProducer = new GroupsV2UpdateMessageProducer(context, descriptionStrategy, Recipient.self().getUuid().get()); GroupsV2UpdateMessageProducer updateMessageProducer = new GroupsV2UpdateMessageProducer(context, descriptionStrategy, Recipient.self().getUuid().get());
if (decryptedGroupV2Context.hasChange() && decryptedGroupV2Context.getGroupState().getRevision() != 0) { if (decryptedGroupV2Context.hasChange() && (decryptedGroupV2Context.getGroupState().getRevision() != 0 || decryptedGroupV2Context.hasPreviousGroupState())) {
return UpdateDescription.concatWithNewLines(updateMessageProducer.describeChanges(decryptedGroupV2Context.getPreviousGroupState(), decryptedGroupV2Context.getChange())); return UpdateDescription.concatWithNewLines(updateMessageProducer.describeChanges(decryptedGroupV2Context.getPreviousGroupState(), decryptedGroupV2Context.getChange()));
} else { } else {
return updateMessageProducer.describeNewGroup(decryptedGroupV2Context.getGroupState(), decryptedGroupV2Context.getChange()); return updateMessageProducer.describeNewGroup(decryptedGroupV2Context.getGroupState(), decryptedGroupV2Context.getChange());