Better group call state management

This commit is contained in:
Fedor Indutny 2024-03-19 10:40:37 -07:00 committed by GitHub
parent 193f344b16
commit 60fa6a11ef
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
3 changed files with 53 additions and 16 deletions

View file

@ -1925,19 +1925,19 @@ export class CallingClass {
envelope: ProcessedEnvelope, envelope: ProcessedEnvelope,
callingMessage: Proto.ICallingMessage callingMessage: Proto.ICallingMessage
): Promise<void> { ): Promise<void> {
log.info('CallingClass.handleCallingMessage()'); const logId = `CallingClass.handleCallingMessage(${envelope.timestamp})`;
const enableIncomingCalls = window.Events.getIncomingCallNotification(); const enableIncomingCalls = window.Events.getIncomingCallNotification();
if (callingMessage.offer && !enableIncomingCalls) { if (callingMessage.offer && !enableIncomingCalls) {
// Drop offers silently if incoming call notifications are disabled. // Drop offers silently if incoming call notifications are disabled.
log.info('Incoming calls are disabled, ignoring call offer.'); log.info(`${logId}: Incoming calls are disabled, ignoring call offer.`);
return; return;
} }
const remoteUserId = envelope.sourceServiceId; const remoteUserId = envelope.sourceServiceId;
const remoteDeviceId = this.parseDeviceId(envelope.sourceDevice); const remoteDeviceId = this.parseDeviceId(envelope.sourceDevice);
if (!remoteUserId || !remoteDeviceId || !this.localDeviceId) { if (!remoteUserId || !remoteDeviceId || !this.localDeviceId) {
log.error('Missing identifier, ignoring call message.'); log.error(`${logId}: Missing identifier, ignoring call message.`);
return; return;
} }
@ -1946,7 +1946,9 @@ export class CallingClass {
const senderIdentityRecord = const senderIdentityRecord =
await storage.protocol.getOrMigrateIdentityRecord(remoteUserId); await storage.protocol.getOrMigrateIdentityRecord(remoteUserId);
if (!senderIdentityRecord) { if (!senderIdentityRecord) {
log.error('Missing sender identity record; ignoring call message.'); log.error(
`${logId}: Missing sender identity record; ignoring call message.`
);
return; return;
} }
const senderIdentityKey = senderIdentityRecord.publicKey.slice(1); // Ignore the type header, it is not used. const senderIdentityKey = senderIdentityRecord.publicKey.slice(1); // Ignore the type header, it is not used.
@ -1955,14 +1957,16 @@ export class CallingClass {
const receiverIdentityRecord = storage.protocol.getIdentityRecord(ourAci); const receiverIdentityRecord = storage.protocol.getIdentityRecord(ourAci);
if (!receiverIdentityRecord) { if (!receiverIdentityRecord) {
log.error('Missing receiver identity record; ignoring call message.'); log.error(
`${logId}: Missing receiver identity record; ignoring call message.`
);
return; return;
} }
const receiverIdentityKey = receiverIdentityRecord.publicKey.slice(1); // Ignore the type header, it is not used. const receiverIdentityKey = receiverIdentityRecord.publicKey.slice(1); // Ignore the type header, it is not used.
const conversation = window.ConversationController.get(remoteUserId); const conversation = window.ConversationController.get(remoteUserId);
if (!conversation) { if (!conversation) {
log.error('Missing conversation; ignoring call message.'); log.error(`${logId}: Missing conversation; ignoring call message.`);
return; return;
} }
@ -1971,7 +1975,8 @@ export class CallingClass {
!conversation.getAccepted({ ignoreEmptyConvo: true }) !conversation.getAccepted({ ignoreEmptyConvo: true })
) { ) {
log.info( log.info(
'Conversation was not approved by user; rejecting call message.' `${logId}: Conversation was not approved by user; ` +
'rejecting call message.'
); );
const { callId } = callingMessage.offer; const { callId } = callingMessage.offer;
@ -2020,7 +2025,7 @@ export class CallingClass {
const messageAgeSec = envelope.messageAgeSec ? envelope.messageAgeSec : 0; const messageAgeSec = envelope.messageAgeSec ? envelope.messageAgeSec : 0;
log.info('CallingClass.handleCallingMessage(): Handling in RingRTC'); log.info(`${logId}: Handling in RingRTC`);
RingRTC.handleCallingMessage( RingRTC.handleCallingMessage(
remoteUserId, remoteUserId,

View file

@ -1198,12 +1198,6 @@ function groupCallStateChange(
const { ourAci } = getState().user; const { ourAci } = getState().user;
strictAssert(ourAci, 'groupCallStateChange failed to fetch our ACI'); strictAssert(ourAci, 'groupCallStateChange failed to fetch our ACI');
log.info(
'groupCallStateChange:',
payload.conversationId,
GroupCallConnectionState[payload.connectionState],
GroupCallJoinState[payload.joinState]
);
dispatch({ dispatch({
type: GROUP_CALL_STATE_CHANGE, type: GROUP_CALL_STATE_CHANGE,
payload: { payload: {
@ -2564,6 +2558,41 @@ export function reducer(
const existingCall = getGroupCall(conversationId, state, callMode); const existingCall = getGroupCall(conversationId, state, callMode);
const existingRingState = getGroupCallRingState(existingCall); const existingRingState = getGroupCallRingState(existingCall);
// Generare a better log line that would help piece together ACIs and
// demuxIds.
const currentlyInCall = new Map(
existingCall?.remoteParticipants.map(({ demuxId, aci }) => [
demuxId,
aci,
]) ?? []
);
const nextInCall = new Map(
remoteParticipants.map(({ demuxId, aci }) => [demuxId, aci]) ?? []
);
const membersLeft = new Array<`${AciString}:${number}`>();
for (const [demuxId, aci] of currentlyInCall) {
if (!nextInCall.has(demuxId)) {
membersLeft.push(`${aci}:${demuxId}`);
}
}
const membersJoined = new Array<`${AciString}:${number}`>();
for (const [demuxId, aci] of nextInCall) {
if (!currentlyInCall.has(demuxId)) {
membersJoined.push(`${aci}:${demuxId}`);
}
}
log.info(
'groupCallStateChange:',
conversationId,
GroupCallConnectionState[connectionState],
GroupCallJoinState[joinState],
`joined={${membersJoined.join(', ')}}`,
`left={${membersLeft.join(', ')}}`
);
const newPeekInfo = peekInfo || const newPeekInfo = peekInfo ||
existingCall?.peekInfo || { existingCall?.peekInfo || {
acis: remoteParticipants.map(({ aci }) => aci), acis: remoteParticipants.map(({ aci }) => aci),

View file

@ -2807,18 +2807,21 @@ export default class MessageReceiver
this.removeFromCache(envelope); this.removeFromCache(envelope);
const logId = `MessageReceiver.handleCallingMessage(${getEnvelopeId(
envelope
)})`;
if ( if (
(envelope.source && this.isBlocked(envelope.source)) || (envelope.source && this.isBlocked(envelope.source)) ||
(envelope.sourceServiceId && (envelope.sourceServiceId &&
this.isServiceIdBlocked(envelope.sourceServiceId)) this.isServiceIdBlocked(envelope.sourceServiceId))
) { ) {
const logId = getEnvelopeId(envelope);
log.info(`${logId}: Dropping calling message from blocked sender`); log.info(`${logId}: Dropping calling message from blocked sender`);
this.removeFromCache(envelope); this.removeFromCache(envelope);
return; return;
} }
log.info(`${logId}: Passing to ringrtc`);
await window.Signal.Services.calling.handleCallingMessage( await window.Signal.Services.calling.handleCallingMessage(
envelope, envelope,
callingMessage callingMessage