Improve timeline rendering performance

This commit is contained in:
trevor-signal 2024-02-27 11:01:25 -05:00 committed by GitHub
parent c319a089d2
commit 167b2f4f1c
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
11 changed files with 329 additions and 106 deletions

View file

@ -1,7 +1,7 @@
// Copyright 2021 Signal Messenger, LLC
// SPDX-License-Identifier: AGPL-3.0-only
import { groupBy, isEmpty, isNumber, isObject, map, omit } from 'lodash';
import { groupBy, isEmpty, isNumber, isObject, map } from 'lodash';
import { createSelector } from 'reselect';
import filesize from 'filesize';
import getDirection from 'direction';
@ -59,7 +59,7 @@ import { getMentionsRegex } from '../../types/Message';
import { SignalService as Proto } from '../../protobuf';
import type { AttachmentType } from '../../types/Attachment';
import { isVoiceMessage, canBeDownloaded } from '../../types/Attachment';
import type { DefaultConversationColorType } from '../../types/Colors';
import { type DefaultConversationColorType } from '../../types/Colors';
import { ReadStatus } from '../../messages/MessageReadStatus';
import type { CallingNotificationType } from '../../util/callingNotification';
@ -74,12 +74,13 @@ import { canEditMessage } from '../../util/canEditMessage';
import { getAccountSelector } from './accounts';
import { getDefaultConversationColor } from './items';
import {
getContactNameColorSelector,
getConversationSelector,
getSelectedMessageIds,
getTargetedMessage,
isMissingRequiredProfileSharing,
getMessages,
getCachedConversationMemberColorsSelector,
getContactNameColor,
} from './conversations';
import {
getIntl,
@ -97,19 +98,17 @@ import type {
import type { AccountSelectorType } from './accounts';
import type { CallSelectorType, CallStateType } from './calling';
import type {
GetConversationByIdType,
ContactNameColorSelectorType,
} from './conversations';
import type { GetConversationByIdType } from './conversations';
import {
SendStatus,
isDelivered,
isFailed,
isMessageJustForMe,
isRead,
isSent,
isViewed,
maxStatus,
isMessageJustForMe,
someRecipientSendStatus,
getHighestSuccessfulRecipientStatus,
someSendStatus,
} from '../../messages/MessageSendState';
import * as log from '../../logging/log';
@ -179,7 +178,7 @@ export type GetPropsForBubbleOptions = Readonly<{
callHistorySelector: CallHistorySelectorType;
activeCall?: CallStateType;
accountSelector: AccountSelectorType;
contactNameColorSelector: ContactNameColorSelectorType;
contactNameColors: Map<string, string>;
defaultConversationColor: DefaultConversationColorType;
}>;
@ -581,7 +580,7 @@ export type GetPropsForMessageOptions = Pick<
| 'selectedMessageIds'
| 'regionCode'
| 'accountSelector'
| 'contactNameColorSelector'
| 'contactNameColors'
| 'defaultConversationColor'
>;
@ -679,7 +678,7 @@ export const getPropsForMessage = (
targetedMessageId,
targetedMessageCounter,
selectedMessageIds,
contactNameColorSelector,
contactNameColors,
defaultConversationColor,
} = options;
@ -708,7 +707,7 @@ export const getPropsForMessage = (
ourNumber,
ourAci,
});
const contactNameColor = contactNameColorSelector(conversationId, authorId);
const contactNameColor = getContactNameColor(contactNameColors, authorId);
const { conversationColor, customColor } = getConversationColorAttributes(
conversation,
@ -786,7 +785,7 @@ export const getMessagePropsSelector = createSelector(
getUserNumber,
getRegionCode,
getAccountSelector,
getContactNameColorSelector,
getCachedConversationMemberColorsSelector,
getTargetedMessage,
getSelectedMessageIds,
getDefaultConversationColor,
@ -798,15 +797,18 @@ export const getMessagePropsSelector = createSelector(
ourNumber,
regionCode,
accountSelector,
contactNameColorSelector,
cachedConversationMemberColorsSelector,
targetedMessage,
selectedMessageIds,
defaultConversationColor
) =>
(message: MessageWithUIFieldsType) => {
const contactNameColors = cachedConversationMemberColorsSelector(
message.conversationId
);
return getPropsForMessage(message, {
accountSelector,
contactNameColorSelector,
contactNameColors,
conversationSelector,
ourConversationId,
ourNumber,
@ -1646,14 +1648,9 @@ export function getMessagePropStatus(
return sent ? 'viewed' : 'sending';
}
const sendStates = Object.values(
const highestSuccessfulStatus = getHighestSuccessfulRecipientStatus(
sendStateByConversationId,
ourConversationId
? omit(sendStateByConversationId, ourConversationId)
: sendStateByConversationId
);
const highestSuccessfulStatus = sendStates.reduce(
(result: SendStatus, { status }) => maxStatus(result, status),
SendStatus.Pending
);
if (
@ -1758,8 +1755,8 @@ function canReplyOrReact(
MessageWithUIFieldsType,
| 'canReplyToStory'
| 'deletedForEveryone'
| 'sendStateByConversationId'
| 'payment'
| 'sendStateByConversationId'
| 'type'
>,
ourConversationId: string | undefined,
@ -1800,11 +1797,10 @@ function canReplyOrReact(
if (isOutgoing(message)) {
return (
isMessageJustForMe(sendStateByConversationId, ourConversationId) ||
someSendStatus(
ourConversationId
? omit(sendStateByConversationId, ourConversationId)
: sendStateByConversationId,
isMessageJustForMe(sendStateByConversationId ?? {}, ourConversationId) ||
someRecipientSendStatus(
sendStateByConversationId ?? {},
ourConversationId,
isSent
)
);
@ -1884,7 +1880,7 @@ export function canDeleteForEveryone(
// Is it too old to delete? (we relax that requirement in Note to Self)
(isMoreRecentThan(message.sent_at, DAY) || isMe) &&
// Is it sent to anyone?
someSendStatus(message.sendStateByConversationId, isSent)
someSendStatus(message.sendStateByConversationId ?? {}, isSent)
);
}
@ -1971,7 +1967,7 @@ const OUTGOING_KEY_ERROR = 'OutgoingIdentityKeyError';
export const getMessageDetails = createSelector(
getAccountSelector,
getContactNameColorSelector,
getCachedConversationMemberColorsSelector,
getConversationSelector,
getIntl,
getRegionCode,
@ -1984,7 +1980,7 @@ export const getMessageDetails = createSelector(
getDefaultConversationColor,
(
accountSelector,
contactNameColorSelector,
cachedConversationMemberColorsSelector,
conversationSelector,
i18n,
regionCode,
@ -2122,7 +2118,9 @@ export const getMessageDetails = createSelector(
errors,
message: getPropsForMessage(message, {
accountSelector,
contactNameColorSelector,
contactNameColors: cachedConversationMemberColorsSelector(
message.conversationId
),
conversationSelector,
ourAci,
ourPni,