Skip to content

Commit

Permalink
Fix group reinvitations when rotating keys
Browse files Browse the repository at this point in the history
tutadb#1838
  • Loading branch information
vitoreiji committed Aug 19, 2024
1 parent 66c480b commit fbac3e6
Show file tree
Hide file tree
Showing 2 changed files with 15 additions and 8 deletions.
1 change: 0 additions & 1 deletion src/common/api/worker/facades/KeyLoaderFacade.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,6 @@ export class KeyLoaderFacade {
* @param groupId the id of the group
* @param requestedVersion the requestedVersion of the key to be loaded
* @param currentGroupKey needs to be set if the user is not a member of the group (e.g. an admin)
* @param attempts how many times should we try reloading the user. This is mainly to prevent infinite recursions. MUST be at max 1.
*/
async loadSymGroupKey(groupId: Id, requestedVersion: number, currentGroupKey?: VersionedKey): Promise<AesKey> {
if (currentGroupKey != null && currentGroupKey.version < requestedVersion) {
Expand Down
22 changes: 15 additions & 7 deletions src/common/api/worker/facades/KeyRotationFacade.ts
Original file line number Diff line number Diff line change
Expand Up @@ -230,8 +230,10 @@ export class KeyRotationFacade {
this.pendingKeyRotations.teamOrCustomerGroupKeyRotations = []
}

let invitationData: GroupInvitationPostData[] = []
if (!isEmpty(this.pendingKeyRotations.userAreaGroupsKeyRotations)) {
const groupKeyRotationData = await this.rotateUserAreaGroupKeys(user)
const { groupKeyRotationData, preparedReInvites } = await this.rotateUserAreaGroupKeys(user)
invitationData = preparedReInvites
if (groupKeyRotationData != null) {
serviceData.groupKeyUpdates = serviceData.groupKeyUpdates.concat(groupKeyRotationData)
}
Expand All @@ -241,6 +243,11 @@ export class KeyRotationFacade {
return
}
await this.serviceExecutor.post(GroupKeyRotationService, serviceData)

if (!isEmpty(invitationData)) {
const shareFacade = await this.shareFacade()
await promiseMap(invitationData, (preparedInvite) => shareFacade.sendGroupInvitationRequest(preparedInvite))
}
}

/**
Expand All @@ -259,14 +266,17 @@ export class KeyRotationFacade {
}

//We assume that the logged-in user is an admin user and that the key encrypting the group key are already pq secure
private async rotateUserAreaGroupKeys(user: User) {
private async rotateUserAreaGroupKeys(user: User): Promise<{
groupKeyRotationData: GroupKeyRotationData[]
preparedReInvites: GroupInvitationPostData[]
}> {
//group key rotation is skipped if
// * user is not an admin user
const adminGroupMembership = user.memberships.find((m) => m.groupType === GroupKeyRotationType.Admin)
if (adminGroupMembership == null) {
// group key rotations are currently only scheduled for single user customers, so this user must be an admin
console.log("Only admin user can rotate the group")
return
return { groupKeyRotationData: [], preparedReInvites: [] }
}

// * the encrypting keys are 128-bit keys. (user group key, admin group key)
Expand All @@ -275,7 +285,7 @@ export class KeyRotationFacade {
if (hasNonQuantumSafeKeys(currentUserGroupKey.object, currentAdminGroupKey.object)) {
// admin group key rotation should be scheduled first on the server, so this should not happen
console.log("Keys cannot be rotated as the encrypting keys are not pq secure")
return
return { groupKeyRotationData: [], preparedReInvites: [] }
}

const groupKeyUpdates = new Array<GroupKeyRotationData>()
Expand All @@ -291,9 +301,7 @@ export class KeyRotationFacade {
preparedReInvites = preparedReInvites.concat(preparedReInvitations)
}

const shareFacade = await this.shareFacade()
await promiseMap(preparedReInvites, (preparedInvite) => shareFacade.sendGroupInvitationRequest(preparedInvite))
return groupKeyUpdates
return { groupKeyRotationData: groupKeyUpdates, preparedReInvites }
}

//We assume that the logged-in user is an admin user and that the key encrypting the group key are already pq secure
Expand Down

0 comments on commit fbac3e6

Please sign in to comment.