mirror of
https://github.com/lux-tel/session-desktop.git
synced 2026-10-30 20:33:24 +00:00
180 lines
5.0 KiB
TypeScript
180 lines
5.0 KiB
TypeScript
import Long from 'long';
|
|
|
|
import { SignalService } from '../../../../protobuf';
|
|
import { Reaction } from '../../../../types/Reaction';
|
|
import { DataMessageWithProfile } from '../DataMessage';
|
|
import { ExpirableMessageParams } from '../ExpirableMessage';
|
|
import { attachmentIdAsLongFromUrl } from '../../../utils';
|
|
import type { WithOutgoingUserProfile } from '../Message';
|
|
import { OutgoingProMessageDetails } from '../../../../types/message/OutgoingProMessageDetails';
|
|
|
|
interface AttachmentPointerCommon {
|
|
contentType?: string;
|
|
key?: Uint8Array;
|
|
size?: number;
|
|
thumbnail?: Uint8Array;
|
|
digest?: Uint8Array;
|
|
fileName?: string;
|
|
flags?: number;
|
|
width?: number;
|
|
height?: number;
|
|
caption?: string;
|
|
}
|
|
|
|
export interface AttachmentPointer extends AttachmentPointerCommon {
|
|
url?: string;
|
|
}
|
|
|
|
export interface AttachmentPointerWithUrl extends AttachmentPointerCommon {
|
|
url: string;
|
|
}
|
|
|
|
export interface Preview {
|
|
url: string;
|
|
title?: string;
|
|
image?: AttachmentPointer;
|
|
}
|
|
|
|
export interface PreviewWithAttachmentUrl {
|
|
url: string;
|
|
title?: string;
|
|
image?: AttachmentPointerWithUrl;
|
|
}
|
|
|
|
interface QuotedAttachmentCommon {
|
|
contentType?: string;
|
|
fileName?: string;
|
|
}
|
|
|
|
export interface QuotedAttachment extends QuotedAttachmentCommon {
|
|
thumbnail?: AttachmentPointer;
|
|
}
|
|
|
|
export interface QuotedAttachmentWithUrl extends QuotedAttachmentCommon {
|
|
thumbnail?: AttachmentPointerWithUrl | QuotedAttachment;
|
|
}
|
|
|
|
export interface Quote {
|
|
id: number;
|
|
author: string;
|
|
}
|
|
|
|
export type OutgoingProMessageDetailsOrProto =
|
|
| OutgoingProMessageDetails
|
|
| SignalService.ProMessage
|
|
| null;
|
|
|
|
export type WithProMessageDetailsOrProto = {
|
|
/**
|
|
* When sending a message we have the ProMessageDetails.
|
|
* When syncing a just sent message, we only have the already built proMessage
|
|
*/
|
|
outgoingProMessageDetails: OutgoingProMessageDetailsOrProto;
|
|
};
|
|
|
|
export type VisibleMessageParams = ExpirableMessageParams &
|
|
WithOutgoingUserProfile &
|
|
WithProMessageDetailsOrProto & {
|
|
attachments?: Array<AttachmentPointerWithUrl>;
|
|
body?: string;
|
|
quote?: Quote;
|
|
preview?: Array<PreviewWithAttachmentUrl>;
|
|
reaction?: Reaction;
|
|
syncTarget?: string; // undefined means it is not a synced message
|
|
};
|
|
|
|
export class VisibleMessage extends DataMessageWithProfile {
|
|
public readonly reaction?: Reaction;
|
|
|
|
private readonly attachments?: Array<AttachmentPointerWithUrl & { deprecatedId: Long }>;
|
|
private readonly body?: string;
|
|
private readonly quote?: Quote;
|
|
|
|
private readonly preview?: Array<PreviewWithAttachmentUrl & { deprecatedId?: Long }>;
|
|
|
|
/// In the case of a sync message, the public key of the person the message was targeted at.
|
|
/// - Note: `null or undefined` if this isn't a sync message.
|
|
private readonly syncTarget?: string;
|
|
|
|
constructor(params: VisibleMessageParams) {
|
|
super({
|
|
createAtNetworkTimestamp: params.createAtNetworkTimestamp,
|
|
identifier: params.identifier,
|
|
expirationType: params.expirationType,
|
|
expireTimer: params.expireTimer,
|
|
outgoingProMessageDetails: params.outgoingProMessageDetails,
|
|
userProfile: params.userProfile,
|
|
});
|
|
this.attachments = params.attachments?.map(attachment => ({
|
|
...attachment,
|
|
deprecatedId: attachmentIdAsLongFromUrl(attachment.url),
|
|
}));
|
|
this.body = params.body;
|
|
this.quote = params.quote;
|
|
|
|
this.preview = params.preview?.map(attachment => ({
|
|
...attachment,
|
|
deprecatedId: attachment.image?.url
|
|
? attachmentIdAsLongFromUrl(attachment.image.url)
|
|
: undefined,
|
|
}));
|
|
this.reaction = params.reaction;
|
|
this.syncTarget = params.syncTarget;
|
|
}
|
|
|
|
public override contentProto(): SignalService.Content {
|
|
// Note: we need to forward the stored proMessage here to the super contentProto()
|
|
return super.contentProto();
|
|
}
|
|
|
|
public override dataProto(): SignalService.DataMessage {
|
|
const dataMessage = super.makeDataProtoWithProfile();
|
|
|
|
if (this.body) {
|
|
dataMessage.body = this.body;
|
|
}
|
|
|
|
dataMessage.attachments = this.attachments ?? [];
|
|
|
|
if (this.reaction) {
|
|
dataMessage.reaction = this.reaction;
|
|
}
|
|
if (this.syncTarget) {
|
|
dataMessage.syncTarget = this.syncTarget;
|
|
}
|
|
|
|
if (this.quote) {
|
|
dataMessage.quote = new SignalService.DataMessage.Quote();
|
|
|
|
dataMessage.quote.id = this.quote.id;
|
|
dataMessage.quote.author = this.quote.author;
|
|
}
|
|
|
|
if (Array.isArray(this.preview)) {
|
|
dataMessage.preview = this.preview.map(preview => {
|
|
const item = new SignalService.DataMessage.Preview();
|
|
if (preview.title) {
|
|
item.title = preview.title;
|
|
}
|
|
if (preview.url) {
|
|
item.url = preview.url;
|
|
}
|
|
item.image = preview.image
|
|
? { ...preview.image, deprecatedId: attachmentIdAsLongFromUrl(preview.image.url) }
|
|
: null;
|
|
|
|
return item;
|
|
});
|
|
}
|
|
|
|
return dataMessage;
|
|
}
|
|
|
|
public isEqual(comparator: VisibleMessage): boolean {
|
|
return (
|
|
this.identifier === comparator.identifier &&
|
|
this.createAtNetworkTimestamp === comparator.createAtNetworkTimestamp
|
|
);
|
|
}
|
|
}
|