@social-mail/social-mail-web-server 1.4.819 → 1.4.821
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/common/globalEnv.d.ts +5 -0
- package/dist/common/globalEnv.d.ts.map +1 -1
- package/dist/common/globalEnv.js +5 -0
- package/dist/common/globalEnv.js.map +1 -1
- package/dist/server/model/entities/LoginSession.d.ts +1 -5
- package/dist/server/model/entities/LoginSession.d.ts.map +1 -1
- package/dist/server/model/entities/LoginSession.js +1 -1
- package/dist/server/model/entities/LoginSession.js.map +1 -1
- package/dist/server/model/entities/Mailbox.d.ts +1 -0
- package/dist/server/model/entities/Mailbox.d.ts.map +1 -1
- package/dist/server/model/entities/Mailbox.js +4 -0
- package/dist/server/model/entities/Mailbox.js.map +1 -1
- package/dist/server/model/entities/MailboxContact.d.ts.map +1 -1
- package/dist/server/model/entities/MailboxContact.js +4 -1
- package/dist/server/model/entities/MailboxContact.js.map +1 -1
- package/dist/server/model/entities/MailboxContactEmail.d.ts.map +1 -1
- package/dist/server/model/entities/MailboxContactEmail.js +4 -1
- package/dist/server/model/entities/MailboxContactEmail.js.map +1 -1
- package/dist/server/model/entities/MailboxEmail.d.ts.map +1 -1
- package/dist/server/model/entities/MailboxEmail.js +4 -1
- package/dist/server/model/entities/MailboxEmail.js.map +1 -1
- package/dist/server/model/events/AccessTokenEvents.d.ts.map +1 -1
- package/dist/server/model/events/AccessTokenEvents.js +1 -0
- package/dist/server/model/events/AccessTokenEvents.js.map +1 -1
- package/dist/server/model/events/LoginSessionEvents.d.ts.map +1 -1
- package/dist/server/model/events/LoginSessionEvents.js +4 -5
- package/dist/server/model/events/LoginSessionEvents.js.map +1 -1
- package/dist/server/model/events/MailboxEvents.d.ts +1 -0
- package/dist/server/model/events/MailboxEvents.d.ts.map +1 -1
- package/dist/server/model/events/MailboxEvents.js +27 -0
- package/dist/server/model/events/MailboxEvents.js.map +1 -1
- package/dist/server/model/events/UserEvents.d.ts +1 -0
- package/dist/server/model/events/UserEvents.d.ts.map +1 -1
- package/dist/server/model/events/UserEvents.js +6 -0
- package/dist/server/model/events/UserEvents.js.map +1 -1
- package/dist/server/services/external-otp-in/ExternalOtpInService.d.ts +10 -0
- package/dist/server/services/external-otp-in/ExternalOtpInService.d.ts.map +1 -0
- package/dist/server/services/external-otp-in/ExternalOtpInService.js +41 -0
- package/dist/server/services/external-otp-in/ExternalOtpInService.js.map +1 -0
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +1 -1
- package/src/common/globalEnv.ts +5 -0
- package/src/server/model/entities/LoginSession.ts +1 -1
- package/src/server/model/entities/Mailbox.ts +3 -0
- package/src/server/model/entities/MailboxContact.ts +4 -1
- package/src/server/model/entities/MailboxContactEmail.ts +4 -1
- package/src/server/model/entities/MailboxEmail.ts +4 -1
- package/src/server/model/events/AccessTokenEvents.ts +2 -0
- package/src/server/model/events/LoginSessionEvents.ts +4 -3
- package/src/server/model/events/MailboxEvents.ts +41 -0
- package/src/server/model/events/UserEvents.ts +9 -0
- package/src/server/services/external-otp-in/ExternalOtpInService.ts +36 -0
package/package.json
CHANGED
package/src/common/globalEnv.ts
CHANGED
|
@@ -27,6 +27,11 @@ export const globalEnv = {
|
|
|
27
27
|
wildcardDomain: process.env.SOCIAL_MAIL_WILDCARD_DOMAIN,
|
|
28
28
|
name: process.env.SOCIAL_MAIL_NAME || "Social Mail",
|
|
29
29
|
secretKey: process.env.SOCIAL_MAIL_SECRET_KEY,
|
|
30
|
+
otpIn:{
|
|
31
|
+
host: process.env.SOCIAL_MAIL_OTP_IN_HOST,
|
|
32
|
+
key: process.env.SOCIAL_MAIL_OTP_IN_KEY,
|
|
33
|
+
secret: process.env.SOCIAL_MAIL_OTP_IN_SECRET,
|
|
34
|
+
},
|
|
30
35
|
port,
|
|
31
36
|
serverID: process.env.SOCIAL_MAIL_SERVER_ID,
|
|
32
37
|
parentApiToken: process.env.SOCIAL_MAIL_PARENT_API_TOKEN,
|
|
@@ -45,7 +45,10 @@ export default class MailboxContact {
|
|
|
45
45
|
@Column({ key: true, dataType: "BigInt", order: 1 })
|
|
46
46
|
@RelateTo(Mailbox,{
|
|
47
47
|
property: (mt) => mt.mailbox,
|
|
48
|
-
inverseProperty: (mb) => mb.mailboxContacts
|
|
48
|
+
inverseProperty: (mb) => mb.mailboxContacts,
|
|
49
|
+
foreignKeyConstraint: {
|
|
50
|
+
cascade: "restrict"
|
|
51
|
+
}
|
|
49
52
|
})
|
|
50
53
|
public mailboxID: number;
|
|
51
54
|
|
|
@@ -26,7 +26,10 @@ export default class MailboxContactEmail {
|
|
|
26
26
|
@Column({ key: true, dataType: "BigInt", order: 1})
|
|
27
27
|
@RelateTo(Mailbox, {
|
|
28
28
|
property: (mte) => mte.mailbox,
|
|
29
|
-
inverseProperty: (mb) => mb.threadEmails
|
|
29
|
+
inverseProperty: (mb) => mb.threadEmails,
|
|
30
|
+
foreignKeyConstraint: {
|
|
31
|
+
cascade: "restrict"
|
|
32
|
+
}
|
|
30
33
|
})
|
|
31
34
|
mailboxID: number;
|
|
32
35
|
|
|
@@ -10,7 +10,10 @@ export default class MailboxEmail {
|
|
|
10
10
|
@Column({ dataType: "BigInt", key: true, order: 1 })
|
|
11
11
|
@RelateTo(Mailbox, {
|
|
12
12
|
property: (me) => me.mailbox,
|
|
13
|
-
inverseProperty: (m) => m.emails
|
|
13
|
+
inverseProperty: (m) => m.emails,
|
|
14
|
+
foreignKeyConstraint: {
|
|
15
|
+
cascade: "restrict"
|
|
16
|
+
}
|
|
14
17
|
})
|
|
15
18
|
mailboxID: number;
|
|
16
19
|
|
|
@@ -11,6 +11,8 @@ export default class AccessTokenEvents extends AuthenticatedEvents<AccessToken>
|
|
|
11
11
|
this.sessionUser.ensureLoggedIn();
|
|
12
12
|
}
|
|
13
13
|
|
|
14
|
+
entity.userID ??= this.sessionUser.userID;
|
|
15
|
+
|
|
14
16
|
entity.secret = "sm-at-" + randomUUID().replaceAll("-", "");
|
|
15
17
|
entity.displaySecret = entity.secret;
|
|
16
18
|
}
|
|
@@ -18,6 +18,7 @@ import Sql from "@entity-access/entity-access/dist/sql/Sql.js";
|
|
|
18
18
|
import { randomUUID } from "crypto";
|
|
19
19
|
import { AppStringHelper } from "../../../common/AppStringHelper.js";
|
|
20
20
|
import IncomingSmsService from "../../services/incoming-sms/IncomingSmsService.js";
|
|
21
|
+
import ExternalOtpInService from "../../services/external-otp-in/ExternalOtpInService.js";
|
|
21
22
|
|
|
22
23
|
export default class LoginSessionEvents extends EntityEvents<LoginSession> {
|
|
23
24
|
|
|
@@ -140,9 +141,9 @@ export default class LoginSessionEvents extends EntityEvents<LoginSession> {
|
|
|
140
141
|
.toArray();
|
|
141
142
|
|
|
142
143
|
if (otpIn.length) {
|
|
143
|
-
const
|
|
144
|
-
|
|
145
|
-
entity.
|
|
144
|
+
const idsCodes = otpIn.map((x) => x.phoneNumber );
|
|
145
|
+
entity.smsConfig = await ServiceProvider.resolve(this, ExternalOtpInService).create(idsCodes);
|
|
146
|
+
entity.smsToken = entity.smsConfig.id;
|
|
146
147
|
}
|
|
147
148
|
|
|
148
149
|
return;
|
|
@@ -13,6 +13,7 @@ import External from "@entity-access/server-pages/dist/decorators/External.js";
|
|
|
13
13
|
import Sql from "@entity-access/entity-access/dist/sql/Sql.js";
|
|
14
14
|
import Page from "@entity-access/server-pages/dist/Page.js";
|
|
15
15
|
import { Prepare } from "@entity-access/server-pages/dist/decorators/Prepare.js";
|
|
16
|
+
import EntityAccessError from "@entity-access/entity-access/dist/common/EntityAccessError.js";
|
|
16
17
|
|
|
17
18
|
export default class MailboxEvents extends AuthenticatedEvents<Mailbox> {
|
|
18
19
|
|
|
@@ -166,4 +167,44 @@ export default class MailboxEvents extends AuthenticatedEvents<Mailbox> {
|
|
|
166
167
|
}
|
|
167
168
|
|
|
168
169
|
}
|
|
170
|
+
|
|
171
|
+
async beforeDelete(entity: Mailbox, entry: ChangeEntry<Mailbox>) {
|
|
172
|
+
this.sessionUser.ensureIsAdmin();
|
|
173
|
+
|
|
174
|
+
const{ db } = this;
|
|
175
|
+
|
|
176
|
+
// if (!entity.deleteVerificationID) {
|
|
177
|
+
// throw new EntityAccessError(`Delete operation not authorized`);
|
|
178
|
+
// }
|
|
179
|
+
|
|
180
|
+
// const [id, accessCode] = entity.deleteVerificationID.split(":") as any[];
|
|
181
|
+
|
|
182
|
+
// const v = await db.verificationTokens.statements.select({} , { verificationID: id, accessCode });
|
|
183
|
+
// if (!v) {
|
|
184
|
+
// throw new EntityAccessError(`Delete operation not authorized`);
|
|
185
|
+
// }
|
|
186
|
+
|
|
187
|
+
await db.fileContents.asQuery()
|
|
188
|
+
.where(entity, (p) => (x) => x.appFiles.some((a) => a.email.mailboxes.some((m) => m.mailboxID === p.mailboxID)))
|
|
189
|
+
.update(void 0, (p) => (x) => ({
|
|
190
|
+
deleted: true
|
|
191
|
+
}));
|
|
192
|
+
|
|
193
|
+
|
|
194
|
+
await db.appFiles.asQuery()
|
|
195
|
+
.delete(entity, (p) => (x) => x.email.mailboxes.some((m) => m.mailboxID === p.mailboxID));
|
|
196
|
+
|
|
197
|
+
|
|
198
|
+
await db.emails.asQuery()
|
|
199
|
+
.delete(entity, (p) => (x) => x.mailboxes.some((m) => m.mailboxID === p.mailboxID));
|
|
200
|
+
|
|
201
|
+
await db.mailboxContactEmails.asQuery()
|
|
202
|
+
.delete(entity, (p) => (x) => x.mailboxID === p.mailboxID);
|
|
203
|
+
|
|
204
|
+
await db.mailboxContactTags.asQuery()
|
|
205
|
+
.delete(entity, (p) => (x) => x.mailboxID === p.mailboxID);
|
|
206
|
+
|
|
207
|
+
await db.mailboxEmails.asQuery()
|
|
208
|
+
.delete(entity, (p) => (x) => x.mailboxID === p.mailboxID);
|
|
209
|
+
}
|
|
169
210
|
}
|
|
@@ -203,10 +203,19 @@ export default class UserEvents extends AuthenticatedEvents<User> {
|
|
|
203
203
|
}
|
|
204
204
|
}
|
|
205
205
|
|
|
206
|
+
async beforeDelete(entity: User, entry: ChangeEntry<User>) {
|
|
207
|
+
this.sessionUser.ensureIsAdmin();
|
|
208
|
+
|
|
209
|
+
const { db } = this;
|
|
210
|
+
await db.contactPhones.asQuery().delete(entity, (p) => (x) => x.contact.userID === p.userID);
|
|
211
|
+
await db.contacts.asQuery().delete(entity, (p) => (x) => x.userID === p.userID);
|
|
212
|
+
}
|
|
213
|
+
|
|
206
214
|
private updatePassword(entity: User, password: string) {
|
|
207
215
|
const passwordSalt = this.cryptoService.generateSalt();
|
|
208
216
|
entity.passwordSalt = passwordSalt;
|
|
209
217
|
entity.passwordHash = this.cryptoService.hash(entity.passwordSalt, password);
|
|
210
218
|
}
|
|
211
219
|
|
|
220
|
+
|
|
212
221
|
}
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
import { RegisterSingleton } from "@entity-access/entity-access/dist/di/di.js";
|
|
2
|
+
import { globalEnv } from "../../../common/globalEnv.js";
|
|
3
|
+
|
|
4
|
+
const headers = {
|
|
5
|
+
authorization: `basic ${Buffer.from(`${globalEnv.otpIn.key}:${globalEnv.otpIn.secret}`).toString("base64")}`
|
|
6
|
+
};
|
|
7
|
+
|
|
8
|
+
const postHeaders = {
|
|
9
|
+
... headers,
|
|
10
|
+
"content-type": "application/json",
|
|
11
|
+
};
|
|
12
|
+
|
|
13
|
+
@RegisterSingleton
|
|
14
|
+
export default class ExternalOtpInService {
|
|
15
|
+
|
|
16
|
+
async create(phoneNumbers: string[]) {
|
|
17
|
+
const rs = await fetch(`https://${globalEnv.otpIn.host}/api/otp-in/create`, {
|
|
18
|
+
method: "POST",
|
|
19
|
+
headers: postHeaders,
|
|
20
|
+
body: JSON.stringify({
|
|
21
|
+
phoneNumbers
|
|
22
|
+
})
|
|
23
|
+
});
|
|
24
|
+
const { id, ui } = await rs.json();
|
|
25
|
+
return { id, ui };
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
async get(id) {
|
|
29
|
+
const rs = await fetch(`https://${globalEnv.otpIn.host}/api/otp-in/get/${id}`, {
|
|
30
|
+
method: "GET",
|
|
31
|
+
headers
|
|
32
|
+
});
|
|
33
|
+
const { success } = await rs.json();
|
|
34
|
+
return { success };
|
|
35
|
+
}
|
|
36
|
+
}
|