Change Phone Number notifications
This commit is contained in:
parent
4b82ac387b
commit
a001882d58
17 changed files with 277 additions and 39 deletions
|
@ -1168,6 +1168,16 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"ChangeNumber--notification": {
|
||||
"message": "$sender$ changed their number to a new number",
|
||||
"description": "Shown in timeline when a member of a conversation changes their phone number",
|
||||
"placeholders": {
|
||||
"sender": {
|
||||
"content": "$1",
|
||||
"example": "Sam"
|
||||
}
|
||||
}
|
||||
},
|
||||
"quoteThumbnailAlt": {
|
||||
"message": "Thumbnail of image from quoted message",
|
||||
"description": "Used in alt tag of thumbnail images inside of an embedded message quote"
|
||||
|
|
|
@ -135,4 +135,5 @@ message AccountRecord {
|
|||
repeated PinnedConversation pinnedConversations = 14;
|
||||
optional uint32 universalExpireTimer = 17;
|
||||
optional bool primarySendsSms = 18;
|
||||
optional string e164 = 19;
|
||||
}
|
||||
|
|
|
@ -2425,6 +2425,45 @@ $timer-icons: '55', '50', '45', '40', '35', '30', '25', '20', '15', '10', '05',
|
|||
}
|
||||
}
|
||||
|
||||
// Module: Change Number Notification
|
||||
|
||||
.module-change-number-notification {
|
||||
@include font-body-2;
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
|
||||
@include light-theme {
|
||||
color: $color-gray-60;
|
||||
}
|
||||
@include dark-theme {
|
||||
color: $color-gray-05;
|
||||
}
|
||||
|
||||
&__icon {
|
||||
height: 16px;
|
||||
width: 16px;
|
||||
display: inline-block;
|
||||
margin-right: 8px;
|
||||
|
||||
@include light-theme {
|
||||
@include color-svg(
|
||||
'../images/icons/v2/phone-right-outline-24.svg',
|
||||
$color-gray-75
|
||||
);
|
||||
}
|
||||
@include dark-theme {
|
||||
@include color-svg(
|
||||
'../images/icons/v2/phone-right-solid-24.svg',
|
||||
$color-gray-15
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Module: Error Boundary
|
||||
|
||||
.module-error-boundary-notification {
|
||||
text-align: center;
|
||||
cursor: pointer;
|
||||
|
|
|
@ -60,6 +60,7 @@ import {
|
|||
ReadSyncEvent,
|
||||
ContactEvent,
|
||||
GroupEvent,
|
||||
EnvelopeEvent,
|
||||
} from './textsecure/messageReceiverEvents';
|
||||
import type { WebAPIType } from './textsecure/WebAPI';
|
||||
import * as universalExpireTimer from './util/universalExpireTimer';
|
||||
|
@ -174,6 +175,10 @@ export async function startApp(): Promise<void> {
|
|||
};
|
||||
}
|
||||
|
||||
messageReceiver.addEventListener(
|
||||
'envelope',
|
||||
queuedEventListener(onEnvelopeReceived, false)
|
||||
);
|
||||
messageReceiver.addEventListener(
|
||||
'message',
|
||||
queuedEventListener(onMessageReceived, false)
|
||||
|
@ -503,17 +508,7 @@ export async function startApp(): Promise<void> {
|
|||
|
||||
accountManager = new window.textsecure.AccountManager(server);
|
||||
accountManager.addEventListener('registration', () => {
|
||||
const ourDeviceId = window.textsecure.storage.user.getDeviceId();
|
||||
const ourNumber = window.textsecure.storage.user.getNumber();
|
||||
const ourUuid = window.textsecure.storage.user.getUuid();
|
||||
const user = {
|
||||
ourConversationId: window.ConversationController.getOurConversationId(),
|
||||
ourDeviceId,
|
||||
ourNumber,
|
||||
ourUuid,
|
||||
regionCode: window.storage.get('regionCode'),
|
||||
};
|
||||
window.Whisper.events.trigger('userChanged', user);
|
||||
window.Whisper.events.trigger('userChanged');
|
||||
|
||||
window.Signal.Util.Registration.markDone();
|
||||
window.log.info('dispatching registration event');
|
||||
|
@ -1210,7 +1205,6 @@ export async function startApp(): Promise<void> {
|
|||
conversationRemoved,
|
||||
removeAllConversations,
|
||||
} = window.reduxActions.conversations;
|
||||
const { userChanged } = window.reduxActions.user;
|
||||
|
||||
convoCollection.on('remove', conversation => {
|
||||
const { id } = conversation || {};
|
||||
|
@ -1254,7 +1248,19 @@ export async function startApp(): Promise<void> {
|
|||
});
|
||||
convoCollection.on('reset', removeAllConversations);
|
||||
|
||||
window.Whisper.events.on('userChanged', userChanged);
|
||||
window.Whisper.events.on('userChanged', () => {
|
||||
const newDeviceId = window.textsecure.storage.user.getDeviceId();
|
||||
const newNumber = window.textsecure.storage.user.getNumber();
|
||||
const newUuid = window.textsecure.storage.user.getUuid();
|
||||
|
||||
window.reduxActions.user.userChanged({
|
||||
ourConversationId: window.ConversationController.getOurConversationId(),
|
||||
ourDeviceId: newDeviceId,
|
||||
ourNumber: newNumber,
|
||||
ourUuid: newUuid,
|
||||
regionCode: window.storage.get('regionCode'),
|
||||
});
|
||||
});
|
||||
|
||||
let shortcutGuideView: WhatIsThis | null = null;
|
||||
|
||||
|
@ -3000,6 +3006,17 @@ export async function startApp(): Promise<void> {
|
|||
maxSize: Infinity,
|
||||
});
|
||||
|
||||
function onEnvelopeReceived({ envelope }: EnvelopeEvent) {
|
||||
const ourUuid = window.textsecure.storage.user.getUuid();
|
||||
if (envelope.sourceUuid && envelope.sourceUuid !== ourUuid) {
|
||||
window.ConversationController.ensureContactIds({
|
||||
e164: envelope.source,
|
||||
uuid: envelope.sourceUuid,
|
||||
highTrust: true,
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
// Note: We do very little in this function, since everything in handleDataMessage is
|
||||
// inside a conversation-specific queue(). Any code here might run before an earlier
|
||||
// message is processed in handleDataMessage().
|
||||
|
|
43
ts/components/conversation/ChangeNumberNotification.tsx
Normal file
43
ts/components/conversation/ChangeNumberNotification.tsx
Normal file
|
@ -0,0 +1,43 @@
|
|||
// Copyright 2021 Signal Messenger, LLC
|
||||
// SPDX-License-Identifier: AGPL-3.0-only
|
||||
|
||||
import React from 'react';
|
||||
|
||||
import { ConversationType } from '../../state/ducks/conversations';
|
||||
import { LocalizerType } from '../../types/Util';
|
||||
import { Intl } from '../Intl';
|
||||
|
||||
import { Timestamp } from './Timestamp';
|
||||
import { Emojify } from './Emojify';
|
||||
|
||||
export type PropsData = {
|
||||
sender: ConversationType;
|
||||
timestamp: number;
|
||||
};
|
||||
|
||||
export type PropsHousekeeping = {
|
||||
i18n: LocalizerType;
|
||||
};
|
||||
|
||||
export type Props = PropsData & PropsHousekeeping;
|
||||
|
||||
const CSS_MODULE = 'module-change-number-notification';
|
||||
|
||||
export const ChangeNumberNotification: React.FC<Props> = props => {
|
||||
const { i18n, sender, timestamp } = props;
|
||||
|
||||
return (
|
||||
<div className={CSS_MODULE}>
|
||||
<span className={`${CSS_MODULE}__icon`} />
|
||||
<Intl
|
||||
id="ChangeNumber--notification"
|
||||
components={{
|
||||
sender: <Emojify text={sender.firstName || sender.title} />,
|
||||
}}
|
||||
i18n={i18n}
|
||||
/>
|
||||
·
|
||||
<Timestamp i18n={i18n} timestamp={timestamp} />
|
||||
</div>
|
||||
);
|
||||
};
|
|
@ -129,6 +129,13 @@ storiesOf('Components/Conversation/TimelineItem', module)
|
|||
type: 'universalTimerNotification',
|
||||
data: null,
|
||||
},
|
||||
{
|
||||
type: 'changeNumberNotification',
|
||||
data: {
|
||||
sender: getDefaultConversation(),
|
||||
timestamp: Date.now(),
|
||||
},
|
||||
},
|
||||
{
|
||||
type: 'callHistory',
|
||||
data: {
|
||||
|
|
|
@ -24,6 +24,10 @@ import {
|
|||
PropsActionsType as DeliveryIssueActionProps,
|
||||
PropsDataType as DeliveryIssueProps,
|
||||
} from './DeliveryIssueNotification';
|
||||
import {
|
||||
ChangeNumberNotification,
|
||||
PropsData as ChangeNumberNotificationProps,
|
||||
} from './ChangeNumberNotification';
|
||||
import { CallingNotificationType } from '../../util/callingNotification';
|
||||
import { InlineNotificationWrapper } from './InlineNotificationWrapper';
|
||||
import {
|
||||
|
@ -95,6 +99,10 @@ type UniversalTimerNotificationType = {
|
|||
type: 'universalTimerNotification';
|
||||
data: null;
|
||||
};
|
||||
type ChangeNumberNotificationType = {
|
||||
type: 'changeNumberNotification';
|
||||
data: ChangeNumberNotificationProps;
|
||||
};
|
||||
type SafetyNumberNotificationType = {
|
||||
type: 'safetyNumberNotification';
|
||||
data: SafetyNumberNotificationProps;
|
||||
|
@ -138,6 +146,7 @@ export type TimelineItemType =
|
|||
| SafetyNumberNotificationType
|
||||
| TimerNotificationType
|
||||
| UniversalTimerNotificationType
|
||||
| ChangeNumberNotificationType
|
||||
| UnsupportedMessageType
|
||||
| VerificationNotificationType;
|
||||
|
||||
|
@ -244,6 +253,10 @@ export class TimelineItem extends React.PureComponent<PropsType> {
|
|||
);
|
||||
} else if (item.type === 'universalTimerNotification') {
|
||||
notification = renderUniversalTimerNotification();
|
||||
} else if (item.type === 'changeNumberNotification') {
|
||||
notification = (
|
||||
<ChangeNumberNotification {...this.props} {...item.data} i18n={i18n} />
|
||||
);
|
||||
} else if (item.type === 'safetyNumberNotification') {
|
||||
notification = (
|
||||
<SafetyNumberNotification {...this.props} {...item.data} i18n={i18n} />
|
||||
|
|
1
ts/model-types.d.ts
vendored
1
ts/model-types.d.ts
vendored
|
@ -141,6 +141,7 @@ export type MessageAttributesType = {
|
|||
| 'profile-change'
|
||||
| 'timer-notification'
|
||||
| 'universal-timer-notification'
|
||||
| 'change-number-notification'
|
||||
| 'verified-change';
|
||||
body?: string;
|
||||
attachments?: Array<AttachmentType>;
|
||||
|
|
|
@ -152,8 +152,6 @@ export class ConversationModel extends window.Backbone
|
|||
|
||||
jobQueue?: typeof window.PQueueType;
|
||||
|
||||
ourNumber?: string;
|
||||
|
||||
ourUuid?: string;
|
||||
|
||||
storeName?: string | null;
|
||||
|
@ -234,7 +232,6 @@ export class ConversationModel extends window.Backbone
|
|||
|
||||
this.storeName = 'conversations';
|
||||
|
||||
this.ourNumber = window.textsecure.storage.user.getNumber();
|
||||
this.ourUuid = window.textsecure.storage.user.getUuid();
|
||||
this.verifiedEnum = window.textsecure.storage.protocol.VerifiedStatus;
|
||||
|
||||
|
@ -1497,6 +1494,11 @@ export class ConversationModel extends window.Backbone
|
|||
const oldValue = this.get('e164');
|
||||
if (e164 && e164 !== oldValue) {
|
||||
this.set('e164', e164);
|
||||
|
||||
if (oldValue) {
|
||||
this.addChangeNumberNotification();
|
||||
}
|
||||
|
||||
window.Signal.Data.updateConversation(this.attributes);
|
||||
this.trigger('idUpdated', this, 'e164', oldValue);
|
||||
}
|
||||
|
@ -2688,7 +2690,7 @@ export class ConversationModel extends window.Backbone
|
|||
sent_at: now,
|
||||
received_at: window.Signal.Util.incrementMessageCounter(),
|
||||
received_at_ms: now,
|
||||
unread: 0,
|
||||
unread: false,
|
||||
changedId: conversationId || this.id,
|
||||
profileChange,
|
||||
// TODO: DESKTOP-722
|
||||
|
@ -2716,23 +2718,30 @@ export class ConversationModel extends window.Backbone
|
|||
}
|
||||
}
|
||||
|
||||
async addUniversalTimerNotification(): Promise<string> {
|
||||
async addNotification(
|
||||
type: MessageAttributesType['type'],
|
||||
extra: Partial<MessageAttributesType> = {}
|
||||
): Promise<string> {
|
||||
const now = Date.now();
|
||||
const message = ({
|
||||
const message: Partial<MessageAttributesType> = {
|
||||
...extra,
|
||||
|
||||
conversationId: this.id,
|
||||
type: 'universal-timer-notification',
|
||||
type,
|
||||
sent_at: now,
|
||||
received_at: window.Signal.Util.incrementMessageCounter(),
|
||||
received_at_ms: now,
|
||||
unread: 0,
|
||||
// TODO: DESKTOP-722
|
||||
} as unknown) as typeof window.Whisper.MessageAttributesType;
|
||||
unread: false,
|
||||
};
|
||||
|
||||
const id = await window.Signal.Data.saveMessage(message);
|
||||
const id = await window.Signal.Data.saveMessage(
|
||||
// TODO: DESKTOP-722
|
||||
message as MessageAttributesType
|
||||
);
|
||||
const model = window.MessageController.register(
|
||||
id,
|
||||
new window.Whisper.Message({
|
||||
...message,
|
||||
...(message as MessageAttributesType),
|
||||
id,
|
||||
})
|
||||
);
|
||||
|
@ -2764,7 +2773,9 @@ export class ConversationModel extends window.Backbone
|
|||
return;
|
||||
}
|
||||
|
||||
const notificationId = await this.addUniversalTimerNotification();
|
||||
const notificationId = await this.addNotification(
|
||||
'universal-timer-notification'
|
||||
);
|
||||
this.set('pendingUniversalTimer', notificationId);
|
||||
}
|
||||
|
||||
|
@ -2797,6 +2808,27 @@ export class ConversationModel extends window.Backbone
|
|||
this.set('pendingUniversalTimer', undefined);
|
||||
}
|
||||
|
||||
async addChangeNumberNotification(): Promise<void> {
|
||||
window.log.info(
|
||||
`Conversation ${this.idForLogging()}: adding change number notification`
|
||||
);
|
||||
|
||||
const convos = [
|
||||
this,
|
||||
...(await window.ConversationController.getAllGroupsInvolvingId(this.id)),
|
||||
];
|
||||
|
||||
const sourceUuid = this.get('uuid');
|
||||
|
||||
await Promise.all(
|
||||
convos.map(convo => {
|
||||
return convo.addNotification('change-number-notification', {
|
||||
sourceUuid,
|
||||
});
|
||||
})
|
||||
);
|
||||
}
|
||||
|
||||
async onReadMessage(
|
||||
message: MessageModel,
|
||||
readAt?: number
|
||||
|
|
|
@ -178,8 +178,6 @@ export class MessageModel extends window.Backbone.Model<MessageAttributesType> {
|
|||
|
||||
INITIAL_PROTOCOL_VERSION?: number;
|
||||
|
||||
OUR_NUMBER?: string;
|
||||
|
||||
OUR_UUID?: string;
|
||||
|
||||
isSelected?: boolean;
|
||||
|
@ -209,7 +207,6 @@ export class MessageModel extends window.Backbone.Model<MessageAttributesType> {
|
|||
|
||||
this.CURRENT_PROTOCOL_VERSION = Proto.DataMessage.ProtocolVersion.CURRENT;
|
||||
this.INITIAL_PROTOCOL_VERSION = Proto.DataMessage.ProtocolVersion.INITIAL;
|
||||
this.OUR_NUMBER = window.textsecure.storage.user.getNumber();
|
||||
this.OUR_UUID = window.textsecure.storage.user.getUuid();
|
||||
|
||||
this.on('change', this.notifyRedux);
|
||||
|
@ -364,7 +361,7 @@ export class MessageModel extends window.Backbone.Model<MessageAttributesType> {
|
|||
this.attributes,
|
||||
findAndFormatContact,
|
||||
ourConversationId,
|
||||
this.OUR_NUMBER,
|
||||
window.textsecure.storage.user.getNumber(),
|
||||
this.OUR_UUID,
|
||||
undefined,
|
||||
undefined,
|
||||
|
@ -1066,7 +1063,7 @@ export class MessageModel extends window.Backbone.Model<MessageAttributesType> {
|
|||
);
|
||||
}
|
||||
|
||||
return this.OUR_NUMBER;
|
||||
return window.textsecure.storage.user.getNumber();
|
||||
}
|
||||
|
||||
getSourceDevice(): string | number | undefined {
|
||||
|
@ -1280,11 +1277,12 @@ export class MessageModel extends window.Backbone.Model<MessageAttributesType> {
|
|||
const quoteWithData = await loadQuoteData(this.get('quote'));
|
||||
const previewWithData = await loadPreviewData(this.get('preview'));
|
||||
const stickerWithData = await loadStickerData(this.get('sticker'));
|
||||
const ourNumber = window.textsecure.storage.user.getNumber();
|
||||
|
||||
// Special-case the self-send case - we send only a sync message
|
||||
if (
|
||||
recipients.length === 1 &&
|
||||
(recipients[0] === this.OUR_NUMBER || recipients[0] === this.OUR_UUID)
|
||||
(recipients[0] === ourNumber || recipients[0] === this.OUR_UUID)
|
||||
) {
|
||||
const dataMessage = await window.textsecure.messaging.getDataMessage({
|
||||
attachments,
|
||||
|
@ -1434,9 +1432,10 @@ export class MessageModel extends window.Backbone.Model<MessageAttributesType> {
|
|||
const quoteWithData = await loadQuoteData(this.get('quote'));
|
||||
const previewWithData = await loadPreviewData(this.get('preview'));
|
||||
const stickerWithData = await loadStickerData(this.get('sticker'));
|
||||
const ourNumber = window.textsecure.storage.user.getNumber();
|
||||
|
||||
// Special-case the self-send case - we send only a sync message
|
||||
if (identifier === this.OUR_NUMBER || identifier === this.OUR_UUID) {
|
||||
if (identifier === ourNumber || identifier === this.OUR_UUID) {
|
||||
const dataMessage = await window.textsecure.messaging.getDataMessage({
|
||||
attachments,
|
||||
body,
|
||||
|
|
|
@ -186,6 +186,11 @@ export async function toAccountRecord(
|
|||
accountRecord.primarySendsSms = Boolean(primarySendsSms);
|
||||
}
|
||||
|
||||
const accountE164 = window.storage.get('accountE164');
|
||||
if (accountE164 !== undefined) {
|
||||
accountRecord.e164 = accountE164;
|
||||
}
|
||||
|
||||
const universalExpireTimer = getUniversalExpireTimer();
|
||||
if (universalExpireTimer) {
|
||||
accountRecord.universalExpireTimer = Number(universalExpireTimer);
|
||||
|
@ -828,6 +833,7 @@ export async function mergeAccountRecord(
|
|||
typingIndicators,
|
||||
primarySendsSms,
|
||||
universalExpireTimer,
|
||||
e164: accountE164,
|
||||
} = accountRecord;
|
||||
|
||||
window.storage.put('read-receipt-setting', Boolean(readReceipts));
|
||||
|
@ -848,6 +854,11 @@ export async function mergeAccountRecord(
|
|||
window.storage.put('primarySendsSms', primarySendsSms);
|
||||
}
|
||||
|
||||
if (typeof accountE164 === 'string') {
|
||||
window.storage.put('accountE164', accountE164);
|
||||
window.storage.user.setNumber(accountE164);
|
||||
}
|
||||
|
||||
setUniversalExpireTimer(universalExpireTimer || 0);
|
||||
|
||||
const PHONE_NUMBER_SHARING_MODE_ENUM =
|
||||
|
|
|
@ -3522,7 +3522,8 @@ async function hasUserInitiatedMessages(
|
|||
'message-history-unsynced',
|
||||
'keychange',
|
||||
'group-v1-migration',
|
||||
'universal-timer-notification'
|
||||
'universal-timer-notification',
|
||||
'change-number-notification'
|
||||
)
|
||||
) AND
|
||||
json_extract(json, '$.expirationTimerUpdate') IS NULL
|
||||
|
@ -4226,7 +4227,8 @@ async function getLastConversationActivity({
|
|||
'message-history-unsynced',
|
||||
'keychange',
|
||||
'group-v1-migration',
|
||||
'universal-timer-notification'
|
||||
'universal-timer-notification',
|
||||
'change-number-notification'
|
||||
)
|
||||
) AND
|
||||
(
|
||||
|
@ -4277,7 +4279,8 @@ async function getLastConversationPreview({
|
|||
'verified-change',
|
||||
'message-history-unsynced',
|
||||
'group-v1-migration',
|
||||
'universal-timer-notification'
|
||||
'universal-timer-notification',
|
||||
'change-number-notification'
|
||||
)
|
||||
) AND NOT
|
||||
(
|
||||
|
|
|
@ -13,6 +13,7 @@ import {
|
|||
import { TimelineItemType } from '../../components/conversation/TimelineItem';
|
||||
import { PropsData } from '../../components/conversation/Message';
|
||||
import { PropsData as TimerNotificationProps } from '../../components/conversation/TimerNotification';
|
||||
import { PropsData as ChangeNumberNotificationProps } from '../../components/conversation/ChangeNumberNotification';
|
||||
import { PropsData as SafetyNumberNotificationProps } from '../../components/conversation/SafetyNumberNotification';
|
||||
import { PropsData as VerificationNotificationProps } from '../../components/conversation/VerificationNotification';
|
||||
import { PropsDataType as GroupsV2Props } from '../../components/conversation/GroupV2Change';
|
||||
|
@ -188,6 +189,12 @@ export function getPropsForBubble(
|
|||
data: null,
|
||||
};
|
||||
}
|
||||
if (isChangeNumberNotification(message)) {
|
||||
return {
|
||||
type: 'changeNumberNotification',
|
||||
data: getPropsForChangeNumberNotification(message, conversationSelector),
|
||||
};
|
||||
}
|
||||
if (isChatSessionRefreshed(message)) {
|
||||
return {
|
||||
type: 'chatSessionRefreshed',
|
||||
|
@ -852,6 +859,24 @@ export function isUniversalTimerNotification(
|
|||
return message.type === 'universal-timer-notification';
|
||||
}
|
||||
|
||||
// Change Number Notification
|
||||
|
||||
export function isChangeNumberNotification(
|
||||
message: MessageAttributesType
|
||||
): boolean {
|
||||
return message.type === 'change-number-notification';
|
||||
}
|
||||
|
||||
function getPropsForChangeNumberNotification(
|
||||
message: MessageAttributesType,
|
||||
conversationSelector: GetConversationByIdType
|
||||
): ChangeNumberNotificationProps {
|
||||
return {
|
||||
sender: conversationSelector(message.sourceUuid),
|
||||
timestamp: message.sent_at,
|
||||
};
|
||||
}
|
||||
|
||||
// Chat Session Refreshed
|
||||
|
||||
export function isChatSessionRefreshed(
|
||||
|
|
|
@ -95,6 +95,7 @@ import {
|
|||
ContactSyncEvent,
|
||||
GroupEvent,
|
||||
GroupSyncEvent,
|
||||
EnvelopeEvent,
|
||||
} from './messageReceiverEvents';
|
||||
|
||||
// TODO: remove once we move away from ArrayBuffers
|
||||
|
@ -459,6 +460,11 @@ export default class MessageReceiver
|
|||
handler: (ev: GroupSyncEvent) => void
|
||||
): void;
|
||||
|
||||
public addEventListener(
|
||||
name: 'envelope',
|
||||
handler: (ev: EnvelopeEvent) => void
|
||||
): void;
|
||||
|
||||
public addEventListener(name: string, handler: EventHandler): void {
|
||||
return super.addEventListener(name, handler);
|
||||
}
|
||||
|
@ -981,8 +987,6 @@ export default class MessageReceiver
|
|||
if (this.stoppingProcessing) {
|
||||
return;
|
||||
}
|
||||
// No decryption is required for delivery receipts, so the decrypted field of
|
||||
// the Unprocessed model will never be set
|
||||
|
||||
if (envelope.content) {
|
||||
await this.innerHandleContentMessage(envelope, plaintext);
|
||||
|
|
|
@ -5,7 +5,11 @@
|
|||
import { PublicKey } from '@signalapp/signal-client';
|
||||
|
||||
import { SignalService as Proto } from '../protobuf';
|
||||
import { ProcessedDataMessage, ProcessedSent } from './Types.d';
|
||||
import {
|
||||
ProcessedEnvelope,
|
||||
ProcessedDataMessage,
|
||||
ProcessedSent,
|
||||
} from './Types.d';
|
||||
import type {
|
||||
ModifiedContactDetails,
|
||||
ModifiedGroupDetails,
|
||||
|
@ -136,6 +140,12 @@ export class GroupSyncEvent extends Event {
|
|||
}
|
||||
}
|
||||
|
||||
export class EnvelopeEvent extends Event {
|
||||
constructor(public readonly envelope: ProcessedEnvelope) {
|
||||
super('envelope');
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Confirmable events below
|
||||
//
|
||||
|
|
|
@ -3,6 +3,7 @@
|
|||
|
||||
import { WebAPICredentials } from '../Types.d';
|
||||
|
||||
import { strictAssert } from '../../util/assert';
|
||||
import { StorageInterface } from '../../types/Storage.d';
|
||||
|
||||
import Helpers from '../Helpers';
|
||||
|
@ -27,6 +28,25 @@ export class User {
|
|||
window.log.info('storage.user: uuid and device id changed');
|
||||
}
|
||||
|
||||
public async setNumber(number: string): Promise<void> {
|
||||
if (this.getNumber() === number) {
|
||||
return;
|
||||
}
|
||||
|
||||
const deviceId = this.getDeviceId();
|
||||
strictAssert(
|
||||
deviceId !== undefined,
|
||||
'Cannot update device number without knowing device id'
|
||||
);
|
||||
|
||||
window.log.info('storage.user: number changed');
|
||||
|
||||
await this.storage.put('number_id', `${number}.${deviceId}`);
|
||||
|
||||
// Notify redux about phone number change
|
||||
window.Whisper.events.trigger('userChanged');
|
||||
}
|
||||
|
||||
public getNumber(): string | undefined {
|
||||
const numberId = this.storage.get('number_id');
|
||||
if (numberId === undefined) return undefined;
|
||||
|
|
3
ts/types/Storage.d.ts
vendored
3
ts/types/Storage.d.ts
vendored
|
@ -77,6 +77,9 @@ export type StorageAccessType = {
|
|||
phoneNumberDiscoverability: PhoneNumberDiscoverability;
|
||||
pinnedConversationIds: Array<string>;
|
||||
primarySendsSms: boolean;
|
||||
// Unlike `number_id` (which also includes device id) this field is only
|
||||
// updated whenever we receive a new storage manifest
|
||||
accountE164: string;
|
||||
typingIndicators: boolean;
|
||||
sealedSenderIndicators: boolean;
|
||||
storageFetchComplete: boolean;
|
||||
|
|
Loading…
Reference in a new issue