blob: 45e9a35797fef9b75ec4f99a2e1f6ea2e0512688 [file] [log] [blame]
simon06527b02022-10-01 15:01:47 -04001import { Socket } from 'socket.io';
2
3import Contact from './Contact';
4import { PromiseExecutor, Session } from './util';
5
6export interface ConversationMember {
7 contact: Contact;
8 role?: 'admin' | 'member' | 'invited' | 'banned' | 'left';
9}
10
11type ConversationInfos = Record<string, unknown>;
12
13export type Message = Record<string, string>;
14type ConversationRequest = PromiseExecutor<Message[]>;
15
16type ConversationListeners = Record<
17 string,
18 {
19 socket: Socket;
20 session: Session;
21 }
22>;
23
24class Conversation {
25 private readonly id: string | undefined;
26 private readonly accountId: string;
27 private readonly members: ConversationMember[];
simon5e32f742022-10-04 18:03:12 -040028 private messages: Message[];
29 private _infos: ConversationInfos;
30 private _requests: Record<string, ConversationRequest>;
31 private _listeners: ConversationListeners;
simon06527b02022-10-01 15:01:47 -040032
33 constructor(id: string | undefined, accountId: string, members?: ConversationMember[]) {
34 this.id = id;
35 this.accountId = accountId;
36 this.members = members || [];
simon5e32f742022-10-04 18:03:12 -040037
38 this.messages = [];
39 this._infos = {};
40 this._requests = {};
41 this._listeners = {};
simon06527b02022-10-01 15:01:47 -040042 }
43
simon5e32f742022-10-04 18:03:12 -040044 static from(accountId: string, object: any) {
simon06527b02022-10-01 15:01:47 -040045 const conversation = new Conversation(
46 object.id,
47 accountId,
simon5e32f742022-10-04 18:03:12 -040048 object.members.map((member: any) => {
simon06527b02022-10-01 15:01:47 -040049 member.contact = Contact.from(member.contact);
50 return member;
51 })
52 );
53 conversation.messages = object.messages;
54 return conversation;
55 }
56 static fromSingleContact(accountId: string, contact: Contact) {
57 return new Conversation(undefined, accountId, [{ contact }]);
58 }
59
60 getId() {
61 return this.id;
62 }
63
64 getAccountId() {
65 return this.accountId;
66 }
67
68 getDisplayName() {
69 if (this.members.length !== 0) {
70 return this.members[0].contact.getDisplayName();
71 }
72 return this.getDisplayUri();
73 }
74
75 getDisplayNameNoFallback() {
76 if (this.members.length !== 0) {
77 return this.members[0].contact.getDisplayNameNoFallback();
78 }
79 }
80
81 async getObject(params?: {
82 memberFilter: (value: ConversationMember, index: number, array: ConversationMember[]) => boolean;
83 }) {
84 const members = params?.memberFilter ? this.members.filter(params.memberFilter) : this.members;
85 return {
86 id: this.id,
87 messages: this.messages,
88 members: await Promise.all(
89 members.map(async (member) => {
90 //Object.assign({}, member);
91 return {
92 role: member.role,
93 contact: await member.contact.getObject(),
94 };
95 })
96 ),
97 };
98 }
99
100 getSummary() {
101 return this.getObject();
102 }
103
104 getDisplayUri() {
105 return this.getId() || this.getFirstMember().contact.getUri();
106 }
107
108 getFirstMember() {
109 return this.members[0];
110 }
111
112 getMembers() {
113 return this.members;
114 }
115
116 addMessage(message: Message) {
117 if (this.messages.length === 0) this.messages.push(message);
118 else if (message.id === this.messages[this.messages.length - 1].linearizedParent) {
119 this.messages.push(message);
120 } else if (message.linearizedParent === this.messages[0].id) {
121 this.messages.unshift(message);
122 } else {
123 console.log("Can't insert message " + message.id);
124 }
125 }
126
127 addLoadedMessages(messages: Message[]) {
128 messages.forEach((message) => this.addMessage(message));
129 }
130
131 getMessages() {
132 return this.messages;
133 }
134
135 set infos(infos: ConversationInfos) {
136 this._infos = infos;
137 }
138
139 get requests(): Record<string, ConversationRequest> {
140 return this._requests;
141 }
142
143 set requests(value: Record<string, ConversationRequest>) {
144 this._requests = value;
145 }
146
147 get listeners(): ConversationListeners {
148 return this._listeners;
149 }
150
151 set listeners(listeners: ConversationListeners) {
152 this._listeners = listeners;
153 }
154}
155
156export default Conversation;