@rpcbase/server 0.380.0 → 0.381.0
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/package.json +15 -72
- package/src/getDerivedKey.ts +20 -0
- package/src/hashPassword.ts +24 -0
- package/src/index.ts +3 -0
- package/src/initServer.ts +68 -0
- package/src/types/index.ts +7 -0
- package/src/types/session.d.ts +10 -0
- package/boot/server.js +0 -36
- package/boot/shared.js +0 -17
- package/boot/worker.js +0 -37
- package/constants/keys.ts +0 -1
- package/database.js +0 -96
- package/express/custom_cors.js +0 -80
- package/express/dev_save_coverage.js +0 -18
- package/express/index.js +0 -93
- package/express/setup_handlers.js +0 -49
- package/files.ts +0 -1
- package/firebase.js +0 -33
- package/get_object_id.ts +0 -39
- package/index.js +0 -17
- package/mailer/index.js +0 -31
- package/mongoose/index.ts +0 -16
- package/mongoose/plugins/disable_default_timestamps_plugin.ts +0 -5
- package/mongoose/plugins/disable_default_version_key_plugin.ts +0 -5
- package/mongoose/plugins/object_id_plugin.ts +0 -31
- package/openai.js +0 -10
- package/publish-output.txt +0 -0
- package/queue/dispatch_indexer_queue.js +0 -22
- package/queue/dispatch_worker_queue.js +0 -38
- package/queue/index.js +0 -110
- package/queue/register_queue_listener.js +0 -180
- package/redis.js +0 -2
- package/rts/index.js +0 -444
- package/search/constants.ts +0 -1
- package/search/ensure_index.ts +0 -53
- package/search/get_client.ts +0 -15
- package/search/index.ts +0 -3
- package/src/access-control/apply_policies.js +0 -104
- package/src/access-control/get_added_fields.js +0 -23
- package/src/access-control/get_policies.js +0 -29
- package/src/access-control/hooks/doc_pre_create.js +0 -26
- package/src/access-control/hooks/query_pre_delete.js +0 -30
- package/src/access-control/index.js +0 -6
- package/src/access-control/mongoose_plugin.js +0 -136
- package/src/api/index.js +0 -6
- package/src/api/stored-values/get_stored_values.js +0 -41
- package/src/api/stored-values/index.js +0 -8
- package/src/api/stored-values/set_stored_values.js +0 -31
- package/src/auth/check_session.js +0 -43
- package/src/auth/forgot_password_email.html +0 -515
- package/src/auth/get_account.js +0 -35
- package/src/auth/get_accounts.js +0 -42
- package/src/auth/index.js +0 -24
- package/src/auth/reset_password.js +0 -70
- package/src/auth/set_new_password.js +0 -63
- package/src/auth/set_new_password_email.html +0 -3
- package/src/auth/sign_in.js +0 -61
- package/src/auth/sign_out.js +0 -11
- package/src/auth/sign_up.js +0 -56
- package/src/client/client_router.js +0 -105
- package/src/files/constants.ts +0 -9
- package/src/files/finalize_file_upload.ts +0 -25
- package/src/files/helpers/get_grid_fs_bucket.ts +0 -20
- package/src/files/index.js +0 -5
- package/src/files/tasks/finalize_file_upload/apply_img_preview.ts +0 -49
- package/src/files/tasks/finalize_file_upload/constants.ts +0 -23
- package/src/files/tasks/finalize_file_upload/download_file.ts +0 -98
- package/src/files/tasks/finalize_file_upload/get_text_vectors.ts +0 -13
- package/src/files/tasks/finalize_file_upload/helpers/convert_pdf_to_png.ts +0 -34
- package/src/files/tasks/finalize_file_upload/helpers/exec.ts +0 -5
- package/src/files/tasks/finalize_file_upload/helpers/get_metadata.ts +0 -18
- package/src/files/tasks/finalize_file_upload/index.ts +0 -53
- package/src/files/tasks/finalize_file_upload/run_ocr.ts +0 -42
- package/src/files/tasks/index.ts +0 -6
- package/src/files/upload_chunk.ts +0 -83
- package/src/helpers/sim_test_inject.ts +0 -21
- package/src/models/Invite.js +0 -23
- package/src/models/Notification.js +0 -44
- package/src/models/Policy.ts +0 -13
- package/src/models/ResetPasswordToken.js +0 -14
- package/src/models/SearchHistory.ts +0 -22
- package/src/models/User.js +0 -42
- package/src/models/UserStoredValues.js +0 -18
- package/src/models/index.js +0 -7
- package/src/notitications/ack_notification.js +0 -26
- package/src/notitications/get_notifications.js +0 -39
- package/src/notitications/llt/README.md +0 -8
- package/src/notitications/llt/get_llts.js +0 -42
- package/src/notitications/set_seen.js +0 -26
- package/src/sessions/index.js +0 -27
- package/src/sessions/session_proxy_middleware.js +0 -18
- package/src/sessions/session_store_middleware.js +0 -106
- package/src/sessions/warning_proxy_middleware.js +0 -17
- package/src/tasks/index.js +0 -8
- package/src/tasks/index_item.js +0 -8
- package/store/index.js +0 -31
|
@@ -1,515 +0,0 @@
|
|
|
1
|
-
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
|
2
|
-
<html xmlns="http://www.w3.org/1999/xhtml">
|
|
3
|
-
<head>
|
|
4
|
-
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
|
5
|
-
<meta name="x-apple-disable-message-reformatting" />
|
|
6
|
-
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
|
|
7
|
-
<meta name="color-scheme" content="light dark" />
|
|
8
|
-
<meta name="supported-color-schemes" content="light dark" />
|
|
9
|
-
<title></title>
|
|
10
|
-
<style type="text/css" rel="stylesheet" media="all">
|
|
11
|
-
/* Base ------------------------------ */
|
|
12
|
-
|
|
13
|
-
@import url("https://fonts.googleapis.com/css?family=Nunito+Sans:400,700&display=swap");
|
|
14
|
-
body {
|
|
15
|
-
width: 100% !important;
|
|
16
|
-
height: 100%;
|
|
17
|
-
margin: 0;
|
|
18
|
-
-webkit-text-size-adjust: none;
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
a {
|
|
22
|
-
color: #3869D4;
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
a img {
|
|
26
|
-
border: none;
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
td {
|
|
30
|
-
word-break: break-word;
|
|
31
|
-
}
|
|
32
|
-
|
|
33
|
-
.preheader {
|
|
34
|
-
display: none !important;
|
|
35
|
-
visibility: hidden;
|
|
36
|
-
mso-hide: all;
|
|
37
|
-
font-size: 1px;
|
|
38
|
-
line-height: 1px;
|
|
39
|
-
max-height: 0;
|
|
40
|
-
max-width: 0;
|
|
41
|
-
opacity: 0;
|
|
42
|
-
overflow: hidden;
|
|
43
|
-
}
|
|
44
|
-
/* Type ------------------------------ */
|
|
45
|
-
|
|
46
|
-
body,
|
|
47
|
-
td,
|
|
48
|
-
th {
|
|
49
|
-
font-family: "Nunito Sans", Helvetica, Arial, sans-serif;
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
h1 {
|
|
53
|
-
margin-top: 0;
|
|
54
|
-
color: #333333;
|
|
55
|
-
font-size: 22px;
|
|
56
|
-
font-weight: bold;
|
|
57
|
-
text-align: left;
|
|
58
|
-
}
|
|
59
|
-
|
|
60
|
-
h2 {
|
|
61
|
-
margin-top: 0;
|
|
62
|
-
color: #333333;
|
|
63
|
-
font-size: 16px;
|
|
64
|
-
font-weight: bold;
|
|
65
|
-
text-align: left;
|
|
66
|
-
}
|
|
67
|
-
|
|
68
|
-
h3 {
|
|
69
|
-
margin-top: 0;
|
|
70
|
-
color: #333333;
|
|
71
|
-
font-size: 14px;
|
|
72
|
-
font-weight: bold;
|
|
73
|
-
text-align: left;
|
|
74
|
-
}
|
|
75
|
-
|
|
76
|
-
td,
|
|
77
|
-
th {
|
|
78
|
-
font-size: 16px;
|
|
79
|
-
}
|
|
80
|
-
|
|
81
|
-
p,
|
|
82
|
-
ul,
|
|
83
|
-
ol,
|
|
84
|
-
blockquote {
|
|
85
|
-
margin: .4em 0 1.1875em;
|
|
86
|
-
font-size: 16px;
|
|
87
|
-
line-height: 1.625;
|
|
88
|
-
}
|
|
89
|
-
|
|
90
|
-
p.sub {
|
|
91
|
-
font-size: 13px;
|
|
92
|
-
}
|
|
93
|
-
/* Utilities ------------------------------ */
|
|
94
|
-
|
|
95
|
-
.align-right {
|
|
96
|
-
text-align: right;
|
|
97
|
-
}
|
|
98
|
-
|
|
99
|
-
.align-left {
|
|
100
|
-
text-align: left;
|
|
101
|
-
}
|
|
102
|
-
|
|
103
|
-
.align-center {
|
|
104
|
-
text-align: center;
|
|
105
|
-
}
|
|
106
|
-
/* Buttons ------------------------------ */
|
|
107
|
-
|
|
108
|
-
.button {
|
|
109
|
-
background-color: #3869D4;
|
|
110
|
-
border-top: 10px solid #3869D4;
|
|
111
|
-
border-right: 18px solid #3869D4;
|
|
112
|
-
border-bottom: 10px solid #3869D4;
|
|
113
|
-
border-left: 18px solid #3869D4;
|
|
114
|
-
display: inline-block;
|
|
115
|
-
color: #FFF;
|
|
116
|
-
text-decoration: none;
|
|
117
|
-
border-radius: 3px;
|
|
118
|
-
box-shadow: 0 2px 3px rgba(0, 0, 0, 0.16);
|
|
119
|
-
-webkit-text-size-adjust: none;
|
|
120
|
-
box-sizing: border-box;
|
|
121
|
-
}
|
|
122
|
-
|
|
123
|
-
.button--green {
|
|
124
|
-
background-color: #22BC66;
|
|
125
|
-
border-top: 10px solid #22BC66;
|
|
126
|
-
border-right: 18px solid #22BC66;
|
|
127
|
-
border-bottom: 10px solid #22BC66;
|
|
128
|
-
border-left: 18px solid #22BC66;
|
|
129
|
-
}
|
|
130
|
-
|
|
131
|
-
.button--red {
|
|
132
|
-
background-color: #FF6136;
|
|
133
|
-
border-top: 10px solid #FF6136;
|
|
134
|
-
border-right: 18px solid #FF6136;
|
|
135
|
-
border-bottom: 10px solid #FF6136;
|
|
136
|
-
border-left: 18px solid #FF6136;
|
|
137
|
-
}
|
|
138
|
-
|
|
139
|
-
@media only screen and (max-width: 500px) {
|
|
140
|
-
.button {
|
|
141
|
-
width: 100% !important;
|
|
142
|
-
text-align: center !important;
|
|
143
|
-
}
|
|
144
|
-
}
|
|
145
|
-
/* Attribute list ------------------------------ */
|
|
146
|
-
|
|
147
|
-
.attributes {
|
|
148
|
-
margin: 0 0 21px;
|
|
149
|
-
}
|
|
150
|
-
|
|
151
|
-
.attributes_content {
|
|
152
|
-
background-color: #F4F4F7;
|
|
153
|
-
padding: 16px;
|
|
154
|
-
}
|
|
155
|
-
|
|
156
|
-
.attributes_item {
|
|
157
|
-
padding: 0;
|
|
158
|
-
}
|
|
159
|
-
/* Related Items ------------------------------ */
|
|
160
|
-
|
|
161
|
-
.related {
|
|
162
|
-
width: 100%;
|
|
163
|
-
margin: 0;
|
|
164
|
-
padding: 25px 0 0 0;
|
|
165
|
-
-premailer-width: 100%;
|
|
166
|
-
-premailer-cellpadding: 0;
|
|
167
|
-
-premailer-cellspacing: 0;
|
|
168
|
-
}
|
|
169
|
-
|
|
170
|
-
.related_item {
|
|
171
|
-
padding: 10px 0;
|
|
172
|
-
color: #CBCCCF;
|
|
173
|
-
font-size: 15px;
|
|
174
|
-
line-height: 18px;
|
|
175
|
-
}
|
|
176
|
-
|
|
177
|
-
.related_item-title {
|
|
178
|
-
display: block;
|
|
179
|
-
margin: .5em 0 0;
|
|
180
|
-
}
|
|
181
|
-
|
|
182
|
-
.related_item-thumb {
|
|
183
|
-
display: block;
|
|
184
|
-
padding-bottom: 10px;
|
|
185
|
-
}
|
|
186
|
-
|
|
187
|
-
.related_heading {
|
|
188
|
-
border-top: 1px solid #CBCCCF;
|
|
189
|
-
text-align: center;
|
|
190
|
-
padding: 25px 0 10px;
|
|
191
|
-
}
|
|
192
|
-
/* Discount Code ------------------------------ */
|
|
193
|
-
|
|
194
|
-
.discount {
|
|
195
|
-
width: 100%;
|
|
196
|
-
margin: 0;
|
|
197
|
-
padding: 24px;
|
|
198
|
-
-premailer-width: 100%;
|
|
199
|
-
-premailer-cellpadding: 0;
|
|
200
|
-
-premailer-cellspacing: 0;
|
|
201
|
-
background-color: #F4F4F7;
|
|
202
|
-
border: 2px dashed #CBCCCF;
|
|
203
|
-
}
|
|
204
|
-
|
|
205
|
-
.discount_heading {
|
|
206
|
-
text-align: center;
|
|
207
|
-
}
|
|
208
|
-
|
|
209
|
-
.discount_body {
|
|
210
|
-
text-align: center;
|
|
211
|
-
font-size: 15px;
|
|
212
|
-
}
|
|
213
|
-
/* Social Icons ------------------------------ */
|
|
214
|
-
|
|
215
|
-
.social {
|
|
216
|
-
width: auto;
|
|
217
|
-
}
|
|
218
|
-
|
|
219
|
-
.social td {
|
|
220
|
-
padding: 0;
|
|
221
|
-
width: auto;
|
|
222
|
-
}
|
|
223
|
-
|
|
224
|
-
.social_icon {
|
|
225
|
-
height: 20px;
|
|
226
|
-
margin: 0 8px 10px 8px;
|
|
227
|
-
padding: 0;
|
|
228
|
-
}
|
|
229
|
-
/* Data table ------------------------------ */
|
|
230
|
-
|
|
231
|
-
.purchase {
|
|
232
|
-
width: 100%;
|
|
233
|
-
margin: 0;
|
|
234
|
-
padding: 35px 0;
|
|
235
|
-
-premailer-width: 100%;
|
|
236
|
-
-premailer-cellpadding: 0;
|
|
237
|
-
-premailer-cellspacing: 0;
|
|
238
|
-
}
|
|
239
|
-
|
|
240
|
-
.purchase_content {
|
|
241
|
-
width: 100%;
|
|
242
|
-
margin: 0;
|
|
243
|
-
padding: 25px 0 0 0;
|
|
244
|
-
-premailer-width: 100%;
|
|
245
|
-
-premailer-cellpadding: 0;
|
|
246
|
-
-premailer-cellspacing: 0;
|
|
247
|
-
}
|
|
248
|
-
|
|
249
|
-
.purchase_item {
|
|
250
|
-
padding: 10px 0;
|
|
251
|
-
color: #51545E;
|
|
252
|
-
font-size: 15px;
|
|
253
|
-
line-height: 18px;
|
|
254
|
-
}
|
|
255
|
-
|
|
256
|
-
.purchase_heading {
|
|
257
|
-
padding-bottom: 8px;
|
|
258
|
-
border-bottom: 1px solid #EAEAEC;
|
|
259
|
-
}
|
|
260
|
-
|
|
261
|
-
.purchase_heading p {
|
|
262
|
-
margin: 0;
|
|
263
|
-
color: #85878E;
|
|
264
|
-
font-size: 12px;
|
|
265
|
-
}
|
|
266
|
-
|
|
267
|
-
.purchase_footer {
|
|
268
|
-
padding-top: 15px;
|
|
269
|
-
border-top: 1px solid #EAEAEC;
|
|
270
|
-
}
|
|
271
|
-
|
|
272
|
-
.purchase_total {
|
|
273
|
-
margin: 0;
|
|
274
|
-
text-align: right;
|
|
275
|
-
font-weight: bold;
|
|
276
|
-
color: #333333;
|
|
277
|
-
}
|
|
278
|
-
|
|
279
|
-
.purchase_total--label {
|
|
280
|
-
padding: 0 15px 0 0;
|
|
281
|
-
}
|
|
282
|
-
|
|
283
|
-
body {
|
|
284
|
-
background-color: #F4F4F7;
|
|
285
|
-
color: #51545E;
|
|
286
|
-
}
|
|
287
|
-
|
|
288
|
-
p {
|
|
289
|
-
color: #51545E;
|
|
290
|
-
}
|
|
291
|
-
|
|
292
|
-
p.sub {
|
|
293
|
-
color: #6B6E76;
|
|
294
|
-
}
|
|
295
|
-
|
|
296
|
-
.email-wrapper {
|
|
297
|
-
width: 100%;
|
|
298
|
-
margin: 0;
|
|
299
|
-
padding: 0;
|
|
300
|
-
-premailer-width: 100%;
|
|
301
|
-
-premailer-cellpadding: 0;
|
|
302
|
-
-premailer-cellspacing: 0;
|
|
303
|
-
background-color: #F4F4F7;
|
|
304
|
-
}
|
|
305
|
-
|
|
306
|
-
.email-content {
|
|
307
|
-
width: 100%;
|
|
308
|
-
margin: 0;
|
|
309
|
-
padding: 0;
|
|
310
|
-
-premailer-width: 100%;
|
|
311
|
-
-premailer-cellpadding: 0;
|
|
312
|
-
-premailer-cellspacing: 0;
|
|
313
|
-
}
|
|
314
|
-
/* Masthead ----------------------- */
|
|
315
|
-
|
|
316
|
-
.email-masthead {
|
|
317
|
-
padding: 25px 0;
|
|
318
|
-
text-align: center;
|
|
319
|
-
}
|
|
320
|
-
|
|
321
|
-
.email-masthead_logo {
|
|
322
|
-
width: 94px;
|
|
323
|
-
}
|
|
324
|
-
|
|
325
|
-
.email-masthead_name {
|
|
326
|
-
font-size: 16px;
|
|
327
|
-
font-weight: bold;
|
|
328
|
-
color: #A8AAAF;
|
|
329
|
-
text-decoration: none;
|
|
330
|
-
text-shadow: 0 1px 0 white;
|
|
331
|
-
}
|
|
332
|
-
/* Body ------------------------------ */
|
|
333
|
-
|
|
334
|
-
.email-body {
|
|
335
|
-
width: 100%;
|
|
336
|
-
margin: 0;
|
|
337
|
-
padding: 0;
|
|
338
|
-
-premailer-width: 100%;
|
|
339
|
-
-premailer-cellpadding: 0;
|
|
340
|
-
-premailer-cellspacing: 0;
|
|
341
|
-
background-color: #FFFFFF;
|
|
342
|
-
}
|
|
343
|
-
|
|
344
|
-
.email-body_inner {
|
|
345
|
-
width: 570px;
|
|
346
|
-
margin: 0 auto;
|
|
347
|
-
padding: 0;
|
|
348
|
-
-premailer-width: 570px;
|
|
349
|
-
-premailer-cellpadding: 0;
|
|
350
|
-
-premailer-cellspacing: 0;
|
|
351
|
-
background-color: #FFFFFF;
|
|
352
|
-
}
|
|
353
|
-
|
|
354
|
-
.email-footer {
|
|
355
|
-
width: 570px;
|
|
356
|
-
margin: 0 auto;
|
|
357
|
-
padding: 0;
|
|
358
|
-
-premailer-width: 570px;
|
|
359
|
-
-premailer-cellpadding: 0;
|
|
360
|
-
-premailer-cellspacing: 0;
|
|
361
|
-
text-align: center;
|
|
362
|
-
}
|
|
363
|
-
|
|
364
|
-
.email-footer p {
|
|
365
|
-
color: #6B6E76;
|
|
366
|
-
}
|
|
367
|
-
|
|
368
|
-
.body-action {
|
|
369
|
-
width: 100%;
|
|
370
|
-
margin: 30px auto;
|
|
371
|
-
padding: 0;
|
|
372
|
-
-premailer-width: 100%;
|
|
373
|
-
-premailer-cellpadding: 0;
|
|
374
|
-
-premailer-cellspacing: 0;
|
|
375
|
-
text-align: center;
|
|
376
|
-
}
|
|
377
|
-
|
|
378
|
-
.body-sub {
|
|
379
|
-
margin-top: 25px;
|
|
380
|
-
padding-top: 25px;
|
|
381
|
-
border-top: 1px solid #EAEAEC;
|
|
382
|
-
}
|
|
383
|
-
|
|
384
|
-
.content-cell {
|
|
385
|
-
padding: 35px;
|
|
386
|
-
}
|
|
387
|
-
/*Media Queries ------------------------------ */
|
|
388
|
-
|
|
389
|
-
@media only screen and (max-width: 600px) {
|
|
390
|
-
.email-body_inner,
|
|
391
|
-
.email-footer {
|
|
392
|
-
width: 100% !important;
|
|
393
|
-
}
|
|
394
|
-
}
|
|
395
|
-
|
|
396
|
-
@media (prefers-color-scheme: dark) {
|
|
397
|
-
body,
|
|
398
|
-
.email-body,
|
|
399
|
-
.email-body_inner,
|
|
400
|
-
.email-content,
|
|
401
|
-
.email-wrapper,
|
|
402
|
-
.email-masthead,
|
|
403
|
-
.email-footer {
|
|
404
|
-
background-color: #333333 !important;
|
|
405
|
-
color: #FFF !important;
|
|
406
|
-
}
|
|
407
|
-
p,
|
|
408
|
-
ul,
|
|
409
|
-
ol,
|
|
410
|
-
blockquote,
|
|
411
|
-
h1,
|
|
412
|
-
h2,
|
|
413
|
-
h3,
|
|
414
|
-
span,
|
|
415
|
-
.purchase_item {
|
|
416
|
-
color: #FFF !important;
|
|
417
|
-
}
|
|
418
|
-
.attributes_content,
|
|
419
|
-
.discount {
|
|
420
|
-
background-color: #222 !important;
|
|
421
|
-
}
|
|
422
|
-
.email-masthead_name {
|
|
423
|
-
text-shadow: none !important;
|
|
424
|
-
}
|
|
425
|
-
}
|
|
426
|
-
|
|
427
|
-
:root {
|
|
428
|
-
color-scheme: light dark;
|
|
429
|
-
supported-color-schemes: light dark;
|
|
430
|
-
}
|
|
431
|
-
</style>
|
|
432
|
-
<!--[if mso]>
|
|
433
|
-
<style type="text/css">
|
|
434
|
-
.f-fallback {
|
|
435
|
-
font-family: Arial, sans-serif;
|
|
436
|
-
}
|
|
437
|
-
</style>
|
|
438
|
-
<![endif]-->
|
|
439
|
-
</head>
|
|
440
|
-
<body>
|
|
441
|
-
<span class="preheader">Your password reset link is ready</span>
|
|
442
|
-
<table class="email-wrapper" width="100%" cellpadding="0" cellspacing="0" role="presentation">
|
|
443
|
-
<tr>
|
|
444
|
-
<td align="center">
|
|
445
|
-
<table class="email-content" width="100%" cellpadding="0" cellspacing="0" role="presentation">
|
|
446
|
-
<tr>
|
|
447
|
-
<td class="email-masthead">
|
|
448
|
-
<a href="https://example.com" class="f-fallback email-masthead_name">
|
|
449
|
-
[Product Name]
|
|
450
|
-
</a>
|
|
451
|
-
</td>
|
|
452
|
-
</tr>
|
|
453
|
-
<!-- Email Body -->
|
|
454
|
-
<tr>
|
|
455
|
-
<td class="email-body" width="100%" cellpadding="0" cellspacing="0">
|
|
456
|
-
<table class="email-body_inner" align="center" width="570" cellpadding="0" cellspacing="0" role="presentation">
|
|
457
|
-
<!-- Body content -->
|
|
458
|
-
<tr>
|
|
459
|
-
<td class="content-cell">
|
|
460
|
-
<div class="f-fallback">
|
|
461
|
-
<h1>Your password reset link</h1>
|
|
462
|
-
<p>The password reset link you have requested is ready. If you did not request a password reset, ignore this email.</p>
|
|
463
|
-
<!-- Action -->
|
|
464
|
-
<table class="body-action" align="center" width="100%" cellpadding="0" cellspacing="0" role="presentation">
|
|
465
|
-
<tr>
|
|
466
|
-
<td align="center">
|
|
467
|
-
<!-- Border based button
|
|
468
|
-
https://litmus.com/blog/a-guide-to-bulletproof-buttons-in-email-design -->
|
|
469
|
-
<table width="100%" border="0" cellspacing="0" cellpadding="0" role="presentation">
|
|
470
|
-
<tr>
|
|
471
|
-
<td align="center">
|
|
472
|
-
<a href="<%= reset_url %>" class="f-fallback button" target="_blank">Reset My Password</a>
|
|
473
|
-
</td>
|
|
474
|
-
</tr>
|
|
475
|
-
</table>
|
|
476
|
-
</td>
|
|
477
|
-
</tr>
|
|
478
|
-
</table>
|
|
479
|
-
|
|
480
|
-
<table class="body-sub" role="presentation">
|
|
481
|
-
<tr>
|
|
482
|
-
<td>
|
|
483
|
-
<p class="f-fallback sub">If you’re having trouble with the button above, copy and paste the URL below into your web browser.</p>
|
|
484
|
-
<p class="f-fallback sub"><%= reset_url %></p>
|
|
485
|
-
</td>
|
|
486
|
-
</tr>
|
|
487
|
-
</table>
|
|
488
|
-
</div>
|
|
489
|
-
</td>
|
|
490
|
-
</tr>
|
|
491
|
-
</table>
|
|
492
|
-
</td>
|
|
493
|
-
</tr>
|
|
494
|
-
<tr>
|
|
495
|
-
<td>
|
|
496
|
-
<table class="email-footer" align="center" width="570" cellpadding="0" cellspacing="0" role="presentation">
|
|
497
|
-
<tr>
|
|
498
|
-
<td class="content-cell" align="center">
|
|
499
|
-
<p class="f-fallback sub align-center">© 2022 [Product Name]. All rights reserved.</p>
|
|
500
|
-
<p class="f-fallback sub align-center">
|
|
501
|
-
[Company Name, LLC]
|
|
502
|
-
<br>1234 Street Rd.
|
|
503
|
-
<br>Suite 1234
|
|
504
|
-
</p>
|
|
505
|
-
</td>
|
|
506
|
-
</tr>
|
|
507
|
-
</table>
|
|
508
|
-
</td>
|
|
509
|
-
</tr>
|
|
510
|
-
</table>
|
|
511
|
-
</td>
|
|
512
|
-
</tr>
|
|
513
|
-
</table>
|
|
514
|
-
</body>
|
|
515
|
-
</html>
|
package/src/auth/get_account.js
DELETED
|
@@ -1,35 +0,0 @@
|
|
|
1
|
-
/* @flow */
|
|
2
|
-
const assert = require("assert")
|
|
3
|
-
|
|
4
|
-
const mongoose = require("../../mongoose")
|
|
5
|
-
const User = require("../models/User")
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
const get_account = async(payload, ctx) => {
|
|
9
|
-
const {user_id} = payload
|
|
10
|
-
assert(user_id, "missing user_id")
|
|
11
|
-
|
|
12
|
-
// verify we are only requesting our own account's info
|
|
13
|
-
const session_user_id = ctx.req.session.user_id
|
|
14
|
-
assert(user_id === session_user_id, "user ids don't match")
|
|
15
|
-
|
|
16
|
-
const user = await User.findOne(
|
|
17
|
-
{_id: user_id},
|
|
18
|
-
{
|
|
19
|
-
email: 1,
|
|
20
|
-
first_name: 1,
|
|
21
|
-
last_name: 1,
|
|
22
|
-
initials: 1,
|
|
23
|
-
avatar_color: 1,
|
|
24
|
-
},
|
|
25
|
-
{ctx},
|
|
26
|
-
)
|
|
27
|
-
|
|
28
|
-
return {
|
|
29
|
-
status: "ok",
|
|
30
|
-
// when user has been deleted return null, this case shouldn't really happen though
|
|
31
|
-
user: user?.toObject() || null,
|
|
32
|
-
}
|
|
33
|
-
}
|
|
34
|
-
|
|
35
|
-
module.exports = get_account
|
package/src/auth/get_accounts.js
DELETED
|
@@ -1,42 +0,0 @@
|
|
|
1
|
-
/* @flow */
|
|
2
|
-
const Promise = require("bluebird")
|
|
3
|
-
|
|
4
|
-
const get_account = require("./get_account")
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
const is_dev = process.env.NODE_ENV === "development"
|
|
8
|
-
|
|
9
|
-
// TODO: RM this method when live reload works in dev mode behind the reverse proxy
|
|
10
|
-
const MAX_CONCURRENCY = 256
|
|
11
|
-
|
|
12
|
-
const get_accounts = async(payload, ctx) => {
|
|
13
|
-
if (!is_dev)
|
|
14
|
-
throw new Error(
|
|
15
|
-
"cannot call the get_accounts api when NODE_ENV isn't development, this api must be called through the reverse proxy",
|
|
16
|
-
)
|
|
17
|
-
|
|
18
|
-
const user_ids = [ctx.req.session.user_id, ctx.req.session.user_id, ctx.req.session.user_id]
|
|
19
|
-
|
|
20
|
-
const accounts = await Promise.map(
|
|
21
|
-
user_ids,
|
|
22
|
-
async(user_id) => {
|
|
23
|
-
if (!user_id) return null
|
|
24
|
-
const res = await get_account({user_id}, ctx)
|
|
25
|
-
|
|
26
|
-
return {
|
|
27
|
-
user: res.user,
|
|
28
|
-
tenant: {
|
|
29
|
-
name: "MOCK",
|
|
30
|
-
},
|
|
31
|
-
}
|
|
32
|
-
},
|
|
33
|
-
{concurrency: MAX_CONCURRENCY},
|
|
34
|
-
)
|
|
35
|
-
|
|
36
|
-
return {
|
|
37
|
-
status: "ok",
|
|
38
|
-
accounts: accounts.filter((account) => !!account),
|
|
39
|
-
}
|
|
40
|
-
}
|
|
41
|
-
|
|
42
|
-
module.exports = get_accounts
|
package/src/auth/index.js
DELETED
|
@@ -1,24 +0,0 @@
|
|
|
1
|
-
/* @flow */
|
|
2
|
-
const sign_up = require("./sign_up")
|
|
3
|
-
const sign_in = require("./sign_in")
|
|
4
|
-
const sign_out = require("./sign_out")
|
|
5
|
-
const reset_password = require("./reset_password")
|
|
6
|
-
const set_new_password = require("./set_new_password")
|
|
7
|
-
const check_session = require("./check_session")
|
|
8
|
-
|
|
9
|
-
const get_accounts = require("./get_accounts")
|
|
10
|
-
const get_account = require("./get_account")
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
module.exports = (app) => {
|
|
14
|
-
app.handler("/rb-api/v1/auth/sign_in", sign_in)
|
|
15
|
-
app.handler("/rb-api/v1/auth/sign_out", sign_out)
|
|
16
|
-
|
|
17
|
-
app.handler("/rb-api/v1/auth/reset_password", reset_password)
|
|
18
|
-
app.handler("/rb-api/v1/auth/set_new_password", set_new_password)
|
|
19
|
-
|
|
20
|
-
app.handler("/rb-api/v1/auth/check_session", check_session)
|
|
21
|
-
|
|
22
|
-
app.handler("/rb-api/v1/auth/get_account", get_account)
|
|
23
|
-
app.handler("/rb-api/v1/auth/get_accounts", get_accounts)
|
|
24
|
-
}
|
|
@@ -1,70 +0,0 @@
|
|
|
1
|
-
/* @flow */
|
|
2
|
-
const _template = require("lodash/template")
|
|
3
|
-
const fs = require("fs")
|
|
4
|
-
const path = require("path")
|
|
5
|
-
const debug = require("debug")
|
|
6
|
-
const isEmail = require("validator/lib/isEmail")
|
|
7
|
-
|
|
8
|
-
const {hash_password} = require("@rpcbase/std/crypto/hash")
|
|
9
|
-
const {get_random_str} = require("@rpcbase/std/crypto/get_random_str")
|
|
10
|
-
|
|
11
|
-
const mailer = require("../../mailer")
|
|
12
|
-
const mongoose = require("../../mongoose")
|
|
13
|
-
|
|
14
|
-
const ResetPasswordToken = require("../models/ResetPasswordToken")
|
|
15
|
-
const User = require("../models/User")
|
|
16
|
-
|
|
17
|
-
const log = debug("rb:auth:reset_password")
|
|
18
|
-
|
|
19
|
-
const {APP_DOMAIN, MAILER_FROM_EMAIL} = process.env
|
|
20
|
-
|
|
21
|
-
const email_tpl = _template(require("./forgot_password_email.html"))
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
const reset_password = async({email}, ctx) => {
|
|
25
|
-
if (!isEmail(email)) {
|
|
26
|
-
throw new Error("reset_password:: invalid email")
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
const user = await User.findOne({email}, null, {ctx})
|
|
30
|
-
|
|
31
|
-
if (!user) {
|
|
32
|
-
log("attempting to reset password for a user that was not found", email)
|
|
33
|
-
// TODO: add random delay to prevent detecting if account exists based on response time
|
|
34
|
-
return {status: "ok"}
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
const token = get_random_str(32)
|
|
38
|
-
const token_hash = await hash_password(token)
|
|
39
|
-
|
|
40
|
-
const reset_token = new ResetPasswordToken({
|
|
41
|
-
user_id: user._id,
|
|
42
|
-
token_hash,
|
|
43
|
-
})
|
|
44
|
-
|
|
45
|
-
await reset_token.save()
|
|
46
|
-
|
|
47
|
-
const reset_url = `https://${APP_DOMAIN}/set-new-password?uid=${user._id}&token=${token}`
|
|
48
|
-
|
|
49
|
-
log("will send reset password email to", user.email)
|
|
50
|
-
|
|
51
|
-
const res = await mailer.sendEmail({
|
|
52
|
-
From: MAILER_FROM_EMAIL,
|
|
53
|
-
To: user.email,
|
|
54
|
-
Subject: "Your password reset link",
|
|
55
|
-
HtmlBody: email_tpl({
|
|
56
|
-
reset_url,
|
|
57
|
-
}),
|
|
58
|
-
})
|
|
59
|
-
|
|
60
|
-
log("res", res)
|
|
61
|
-
|
|
62
|
-
// cleanup if email wasn't sent
|
|
63
|
-
if (res.Message !== "OK") {
|
|
64
|
-
await reset_token.delete()
|
|
65
|
-
}
|
|
66
|
-
|
|
67
|
-
return {status: "ok"}
|
|
68
|
-
}
|
|
69
|
-
|
|
70
|
-
module.exports = reset_password
|