@wopr-network/platform-core 1.53.0 → 1.55.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/dist/auth/better-auth.js +5 -0
- package/dist/email/default-templates.js +49 -49
- package/dist/email/notification-templates.js +154 -111
- package/dist/email/templates.d.ts +9 -9
- package/dist/email/templates.js +61 -55
- package/dist/email/templates.test.js +1 -1
- package/package.json +1 -1
- package/src/auth/better-auth.ts +5 -0
- package/src/email/default-templates.ts +56 -56
- package/src/email/notification-templates.ts +155 -107
- package/src/email/templates.test.ts +1 -1
- package/src/email/templates.ts +67 -47
|
@@ -177,7 +177,7 @@ describe("all templates", () => {
|
|
|
177
177
|
expect(t.html).toContain("<!DOCTYPE html>");
|
|
178
178
|
expect(t.html).toContain("<html>");
|
|
179
179
|
expect(t.html).toContain("</html>");
|
|
180
|
-
expect(t.html).toContain("WOPR
|
|
180
|
+
expect(t.html).toContain("WOPR");
|
|
181
181
|
expect(t.subject.length).toBeGreaterThan(0);
|
|
182
182
|
expect(t.text.length).toBeGreaterThan(0);
|
|
183
183
|
}
|
package/src/email/templates.ts
CHANGED
|
@@ -12,7 +12,7 @@ import { escapeHtml } from "./resend-adapter.js";
|
|
|
12
12
|
// Shared layout helpers
|
|
13
13
|
// ---------------------------------------------------------------------------
|
|
14
14
|
|
|
15
|
-
function wrapHtml(title: string, bodyContent: string): string {
|
|
15
|
+
function wrapHtml(title: string, bodyContent: string, brandName = "WOPR"): string {
|
|
16
16
|
return `<!DOCTYPE html>
|
|
17
17
|
<html>
|
|
18
18
|
<head>
|
|
@@ -27,7 +27,7 @@ function wrapHtml(title: string, bodyContent: string): string {
|
|
|
27
27
|
<table role="presentation" style="width: 600px; margin: 0 auto; background-color: #ffffff; border-radius: 8px; box-shadow: 0 2px 4px rgba(0,0,0,0.1);">
|
|
28
28
|
${bodyContent}
|
|
29
29
|
</table>
|
|
30
|
-
<p style="margin-top: 20px; color: #a0aec0; font-size: 12px;">© ${new Date().getFullYear()}
|
|
30
|
+
<p style="margin-top: 20px; color: #a0aec0; font-size: 12px;">© ${new Date().getFullYear()} ${escapeHtml(brandName)}. All rights reserved.</p>
|
|
31
31
|
</td>
|
|
32
32
|
</tr>
|
|
33
33
|
</table>
|
|
@@ -116,57 +116,61 @@ export interface TemplateResult {
|
|
|
116
116
|
// 1. Verify Email
|
|
117
117
|
// ---------------------------------------------------------------------------
|
|
118
118
|
|
|
119
|
-
export function verifyEmailTemplate(verifyUrl: string, email: string): TemplateResult {
|
|
119
|
+
export function verifyEmailTemplate(verifyUrl: string, email: string, brandName = "WOPR"): TemplateResult {
|
|
120
120
|
const escapedEmail = escapeHtml(email);
|
|
121
121
|
const escapedUrl = escapeHtml(verifyUrl);
|
|
122
|
+
const b = escapeHtml(brandName);
|
|
122
123
|
|
|
123
124
|
const html = wrapHtml(
|
|
124
125
|
"Verify Your Email",
|
|
125
126
|
[
|
|
126
127
|
heading("Verify Your Email"),
|
|
127
|
-
paragraph(`<p>Thanks for signing up for
|
|
128
|
+
paragraph(`<p>Thanks for signing up for ${b}! Please verify your email address (<strong>${escapedEmail}</strong>) to activate your account.</p>
|
|
128
129
|
<p>Click the button below to verify. This link will expire in 24 hours.</p>`),
|
|
129
130
|
button(verifyUrl, "Verify Email"),
|
|
130
131
|
paragraph(`<p style="color: #718096; font-size: 14px;">Or copy and paste this URL into your browser:</p>
|
|
131
132
|
<p style="word-break: break-all; color: #2563eb; font-size: 14px;">${escapedUrl}</p>`),
|
|
132
|
-
footer(
|
|
133
|
+
footer(`If you didn't create a ${b} account, you can safely ignore this email.`),
|
|
133
134
|
].join("\n"),
|
|
135
|
+
brandName,
|
|
134
136
|
);
|
|
135
137
|
|
|
136
138
|
const text = `Verify Your Email
|
|
137
139
|
|
|
138
|
-
Thanks for signing up for
|
|
140
|
+
Thanks for signing up for ${brandName}! Please verify your email address (${email}) to activate your account.
|
|
139
141
|
|
|
140
142
|
Click the link below to verify. This link will expire in 24 hours.
|
|
141
143
|
|
|
142
144
|
${verifyUrl}
|
|
143
145
|
|
|
144
|
-
If you didn't create a
|
|
146
|
+
If you didn't create a ${brandName} account, you can safely ignore this email.
|
|
145
147
|
|
|
146
|
-
(c) ${new Date().getFullYear()}
|
|
148
|
+
(c) ${new Date().getFullYear()} ${brandName}. All rights reserved.`;
|
|
147
149
|
|
|
148
|
-
return { subject:
|
|
150
|
+
return { subject: `Verify your ${brandName} account`, html, text };
|
|
149
151
|
}
|
|
150
152
|
|
|
151
153
|
// ---------------------------------------------------------------------------
|
|
152
154
|
// 2. Welcome
|
|
153
155
|
// ---------------------------------------------------------------------------
|
|
154
156
|
|
|
155
|
-
export function welcomeTemplate(email: string): TemplateResult {
|
|
157
|
+
export function welcomeTemplate(email: string, brandName = "WOPR"): TemplateResult {
|
|
156
158
|
const escapedEmail = escapeHtml(email);
|
|
159
|
+
const b = escapeHtml(brandName);
|
|
157
160
|
|
|
158
161
|
const html = wrapHtml(
|
|
159
|
-
|
|
162
|
+
`Welcome to ${b}`,
|
|
160
163
|
[
|
|
161
|
-
heading(
|
|
164
|
+
heading(`Welcome to ${b}!`),
|
|
162
165
|
paragraph(`<p>Hi <strong>${escapedEmail}</strong>,</p>
|
|
163
166
|
<p>Your email has been verified and your account is now active. You've been granted <strong>$5.00 in free credits</strong> to get started.</p>
|
|
164
167
|
<p>You can now create bots, connect them to Discord, Slack, and more.</p>`),
|
|
165
168
|
footer("Happy building!"),
|
|
166
169
|
].join("\n"),
|
|
170
|
+
brandName,
|
|
167
171
|
);
|
|
168
172
|
|
|
169
|
-
const text = `Welcome to
|
|
173
|
+
const text = `Welcome to ${brandName}!
|
|
170
174
|
|
|
171
175
|
Hi ${email},
|
|
172
176
|
|
|
@@ -176,38 +180,40 @@ You can now create bots, connect them to Discord, Slack, and more.
|
|
|
176
180
|
|
|
177
181
|
Happy building!
|
|
178
182
|
|
|
179
|
-
(c) ${new Date().getFullYear()}
|
|
183
|
+
(c) ${new Date().getFullYear()} ${brandName}. All rights reserved.`;
|
|
180
184
|
|
|
181
|
-
return { subject:
|
|
185
|
+
return { subject: `Welcome to ${brandName}`, html, text };
|
|
182
186
|
}
|
|
183
187
|
|
|
184
188
|
// ---------------------------------------------------------------------------
|
|
185
189
|
// 3. Password Reset (supersedes WOP-346 inline template)
|
|
186
190
|
// ---------------------------------------------------------------------------
|
|
187
191
|
|
|
188
|
-
export function passwordResetEmailTemplate(resetUrl: string, email: string): TemplateResult {
|
|
192
|
+
export function passwordResetEmailTemplate(resetUrl: string, email: string, brandName = "WOPR"): TemplateResult {
|
|
189
193
|
const escapedEmail = escapeHtml(email);
|
|
190
194
|
const escapedUrl = escapeHtml(resetUrl);
|
|
195
|
+
const b = escapeHtml(brandName);
|
|
191
196
|
|
|
192
197
|
const html = wrapHtml(
|
|
193
198
|
"Reset Your Password",
|
|
194
199
|
[
|
|
195
200
|
heading("Reset Your Password"),
|
|
196
201
|
paragraph(`<p>Hi there,</p>
|
|
197
|
-
<p>You requested a password reset for your
|
|
202
|
+
<p>You requested a password reset for your ${b} account (<strong>${escapedEmail}</strong>).</p>
|
|
198
203
|
<p>Click the button below to create a new password. This link will expire in 1 hour.</p>`),
|
|
199
204
|
button(resetUrl, "Reset Password"),
|
|
200
205
|
paragraph(`<p style="color: #718096; font-size: 14px;">Or copy and paste this URL into your browser:</p>
|
|
201
206
|
<p style="word-break: break-all; color: #2563eb; font-size: 14px;">${escapedUrl}</p>`),
|
|
202
207
|
footer("If you didn't request this password reset, you can safely ignore this email."),
|
|
203
208
|
].join("\n"),
|
|
209
|
+
brandName,
|
|
204
210
|
);
|
|
205
211
|
|
|
206
212
|
const text = `Reset Your Password
|
|
207
213
|
|
|
208
214
|
Hi there,
|
|
209
215
|
|
|
210
|
-
You requested a password reset for your
|
|
216
|
+
You requested a password reset for your ${brandName} account (${email}).
|
|
211
217
|
|
|
212
218
|
Click the link below to create a new password. This link will expire in 1 hour.
|
|
213
219
|
|
|
@@ -215,9 +221,9 @@ ${resetUrl}
|
|
|
215
221
|
|
|
216
222
|
If you didn't request this password reset, you can safely ignore this email.
|
|
217
223
|
|
|
218
|
-
(c) ${new Date().getFullYear()}
|
|
224
|
+
(c) ${new Date().getFullYear()} ${brandName}. All rights reserved.`;
|
|
219
225
|
|
|
220
|
-
return { subject:
|
|
226
|
+
return { subject: `Reset your ${brandName} password`, html, text };
|
|
221
227
|
}
|
|
222
228
|
|
|
223
229
|
// ---------------------------------------------------------------------------
|
|
@@ -229,9 +235,11 @@ export function creditPurchaseTemplate(
|
|
|
229
235
|
amountDollars: string,
|
|
230
236
|
newBalanceDollars?: string,
|
|
231
237
|
creditsUrl?: string,
|
|
238
|
+
brandName = "WOPR",
|
|
232
239
|
): TemplateResult {
|
|
233
240
|
const escapedEmail = escapeHtml(email);
|
|
234
241
|
const escapedAmount = escapeHtml(amountDollars);
|
|
242
|
+
const b = escapeHtml(brandName);
|
|
235
243
|
const balanceLine = newBalanceDollars
|
|
236
244
|
? `<p>Your new balance is <strong>${escapeHtml(newBalanceDollars)}</strong>.</p>`
|
|
237
245
|
: "<p>Your updated balance is now available in your dashboard.</p>";
|
|
@@ -242,25 +250,25 @@ export function creditPurchaseTemplate(
|
|
|
242
250
|
const parts = [
|
|
243
251
|
heading("Credits Added to Your Account"),
|
|
244
252
|
paragraph(`<p>Hi <strong>${escapedEmail}</strong>,</p>
|
|
245
|
-
<p><strong>${escapedAmount}</strong> in credits has been added to your
|
|
253
|
+
<p><strong>${escapedAmount}</strong> in credits has been added to your ${b} account.</p>
|
|
246
254
|
${balanceLine}`),
|
|
247
255
|
];
|
|
248
256
|
if (creditsUrl) parts.push(button(creditsUrl, "View Credits"));
|
|
249
|
-
parts.push(footer(
|
|
257
|
+
parts.push(footer(`Thank you for supporting ${b}!`));
|
|
250
258
|
parts.push(unsubscribeFooter(creditsUrl ? buildUnsubscribeUrl(creditsUrl) : undefined));
|
|
251
259
|
|
|
252
|
-
const html = wrapHtml("Credits Added", parts.join("\n"));
|
|
260
|
+
const html = wrapHtml("Credits Added", parts.join("\n"), brandName);
|
|
253
261
|
|
|
254
262
|
const text = `Credits Added to Your Account
|
|
255
263
|
|
|
256
264
|
Hi ${email},
|
|
257
265
|
|
|
258
|
-
${amountDollars} in credits has been added to your
|
|
266
|
+
${amountDollars} in credits has been added to your ${brandName} account.
|
|
259
267
|
${balanceTextLine}
|
|
260
268
|
${creditsUrl ? `\nView your credits: ${creditsUrl}` : ""}
|
|
261
|
-
Thank you for supporting
|
|
269
|
+
Thank you for supporting ${brandName}!${unsubscribeText(creditsUrl ? buildUnsubscribeUrl(creditsUrl) : undefined)}
|
|
262
270
|
|
|
263
|
-
(c) ${new Date().getFullYear()}
|
|
271
|
+
(c) ${new Date().getFullYear()} ${brandName}. All rights reserved.`;
|
|
264
272
|
|
|
265
273
|
return { subject: "Credits added to your account", html, text };
|
|
266
274
|
}
|
|
@@ -274,9 +282,11 @@ export function lowBalanceTemplate(
|
|
|
274
282
|
balanceDollars: string,
|
|
275
283
|
estimatedDaysRemaining?: number,
|
|
276
284
|
creditsUrl?: string,
|
|
285
|
+
brandName = "WOPR",
|
|
277
286
|
): TemplateResult {
|
|
278
287
|
const escapedEmail = escapeHtml(email);
|
|
279
288
|
const escapedBalance = escapeHtml(balanceDollars);
|
|
289
|
+
const b = escapeHtml(brandName);
|
|
280
290
|
const daysLine =
|
|
281
291
|
estimatedDaysRemaining != null
|
|
282
292
|
? `<p>At your current usage, your credits will run out in approximately <strong>${estimatedDaysRemaining} day${estimatedDaysRemaining === 1 ? "" : "s"}</strong>.</p>`
|
|
@@ -287,9 +297,9 @@ export function lowBalanceTemplate(
|
|
|
287
297
|
: "";
|
|
288
298
|
|
|
289
299
|
const parts = [
|
|
290
|
-
heading(
|
|
300
|
+
heading(`Your ${b} Credits Are Running Low`),
|
|
291
301
|
paragraph(`<p>Hi <strong>${escapedEmail}</strong>,</p>
|
|
292
|
-
<p>Your
|
|
302
|
+
<p>Your ${b} credit balance is now <strong>${escapedBalance}</strong>. When your balance reaches $0, your bots will be paused.</p>
|
|
293
303
|
${daysLine}
|
|
294
304
|
<p>Top up your credits to keep your bots running.</p>`),
|
|
295
305
|
];
|
|
@@ -297,20 +307,20 @@ export function lowBalanceTemplate(
|
|
|
297
307
|
parts.push(footer("This is an automated notification based on your account balance."));
|
|
298
308
|
parts.push(unsubscribeFooter(creditsUrl ? buildUnsubscribeUrl(creditsUrl) : undefined));
|
|
299
309
|
|
|
300
|
-
const html = wrapHtml("Low Balance", parts.join("\n"));
|
|
310
|
+
const html = wrapHtml("Low Balance", parts.join("\n"), brandName);
|
|
301
311
|
|
|
302
|
-
const text = `Your
|
|
312
|
+
const text = `Your ${brandName} Credits Are Running Low
|
|
303
313
|
|
|
304
314
|
Hi ${email},
|
|
305
315
|
|
|
306
|
-
Your
|
|
316
|
+
Your ${brandName} credit balance is now ${balanceDollars}. When your balance reaches $0, your bots will be paused.
|
|
307
317
|
${daysTextLine ? `${daysTextLine}\n` : ""}
|
|
308
318
|
Top up your credits to keep your bots running.
|
|
309
319
|
${creditsUrl ? `\nBuy credits: ${creditsUrl}` : ""}${unsubscribeText(creditsUrl ? buildUnsubscribeUrl(creditsUrl) : undefined)}
|
|
310
320
|
|
|
311
|
-
(c) ${new Date().getFullYear()}
|
|
321
|
+
(c) ${new Date().getFullYear()} ${brandName}. All rights reserved.`;
|
|
312
322
|
|
|
313
|
-
return { subject:
|
|
323
|
+
return { subject: `Your ${brandName} credits are running low`, html, text };
|
|
314
324
|
}
|
|
315
325
|
|
|
316
326
|
// ---------------------------------------------------------------------------
|
|
@@ -322,6 +332,8 @@ export function botSuspendedTemplate(
|
|
|
322
332
|
botName: string,
|
|
323
333
|
reason: string,
|
|
324
334
|
creditsUrl?: string,
|
|
335
|
+
brandName = "WOPR",
|
|
336
|
+
supportEmail = "support@wopr.bot",
|
|
325
337
|
): TemplateResult {
|
|
326
338
|
const escapedEmail = escapeHtml(email);
|
|
327
339
|
const escapedBotName = escapeHtml(botName);
|
|
@@ -335,10 +347,10 @@ export function botSuspendedTemplate(
|
|
|
335
347
|
<p>Buy credits to reactivate instantly. Your data is preserved for 30 days.</p>`),
|
|
336
348
|
];
|
|
337
349
|
if (creditsUrl) parts.push(button(creditsUrl, "Buy Credits to Reactivate"));
|
|
338
|
-
parts.push(footer(
|
|
350
|
+
parts.push(footer(`If you need help, reply to this email or contact ${escapeHtml(supportEmail)}.`));
|
|
339
351
|
parts.push(unsubscribeFooter(creditsUrl ? buildUnsubscribeUrl(creditsUrl) : undefined));
|
|
340
352
|
|
|
341
|
-
const html = wrapHtml("Bot Suspended", parts.join("\n"));
|
|
353
|
+
const html = wrapHtml("Bot Suspended", parts.join("\n"), brandName);
|
|
342
354
|
|
|
343
355
|
const text = `Your Bot Has Been Suspended
|
|
344
356
|
|
|
@@ -350,9 +362,9 @@ Reason: ${reason}
|
|
|
350
362
|
|
|
351
363
|
Buy credits to reactivate instantly. Your data is preserved for 30 days.
|
|
352
364
|
${creditsUrl ? `\nBuy credits: ${creditsUrl}` : ""}
|
|
353
|
-
If you need help, reply to this email or contact
|
|
365
|
+
If you need help, reply to this email or contact ${supportEmail}.${unsubscribeText(creditsUrl ? buildUnsubscribeUrl(creditsUrl) : undefined)}
|
|
354
366
|
|
|
355
|
-
(c) ${new Date().getFullYear()}
|
|
367
|
+
(c) ${new Date().getFullYear()} ${brandName}. All rights reserved.`;
|
|
356
368
|
|
|
357
369
|
return { subject: "Your bot has been suspended", html, text };
|
|
358
370
|
}
|
|
@@ -366,6 +378,7 @@ export function botDestructionTemplate(
|
|
|
366
378
|
botName: string,
|
|
367
379
|
daysRemaining: number,
|
|
368
380
|
creditsUrl?: string,
|
|
381
|
+
brandName = "WOPR",
|
|
369
382
|
): TemplateResult {
|
|
370
383
|
const escapedEmail = escapeHtml(email);
|
|
371
384
|
const escapedBotName = escapeHtml(botName);
|
|
@@ -388,7 +401,7 @@ export function botDestructionTemplate(
|
|
|
388
401
|
);
|
|
389
402
|
parts.push(unsubscribeFooter(creditsUrl ? buildUnsubscribeUrl(creditsUrl) : undefined));
|
|
390
403
|
|
|
391
|
-
const html = wrapHtml("Bot Data Deletion", parts.join("\n"));
|
|
404
|
+
const html = wrapHtml("Bot Data Deletion", parts.join("\n"), brandName);
|
|
392
405
|
|
|
393
406
|
const text = `URGENT: Bot Data Will Be Deleted
|
|
394
407
|
|
|
@@ -400,7 +413,7 @@ Buy credits before the deadline to save your data.
|
|
|
400
413
|
${creditsUrl ? `\nBuy credits now: ${creditsUrl}` : ""}
|
|
401
414
|
This action is irreversible. All bot configuration, history, and connected services will be removed.${unsubscribeText(creditsUrl ? buildUnsubscribeUrl(creditsUrl) : undefined)}
|
|
402
415
|
|
|
403
|
-
(c) ${new Date().getFullYear()}
|
|
416
|
+
(c) ${new Date().getFullYear()} ${brandName}. All rights reserved.`;
|
|
404
417
|
|
|
405
418
|
return { subject: `URGENT: Your bot data will be deleted in ${daysRemaining} days`, html, text };
|
|
406
419
|
}
|
|
@@ -409,7 +422,12 @@ This action is irreversible. All bot configuration, history, and connected servi
|
|
|
409
422
|
// 8. Data Deleted Confirmation
|
|
410
423
|
// ---------------------------------------------------------------------------
|
|
411
424
|
|
|
412
|
-
export function dataDeletedTemplate(
|
|
425
|
+
export function dataDeletedTemplate(
|
|
426
|
+
email: string,
|
|
427
|
+
creditsUrl?: string,
|
|
428
|
+
brandName = "WOPR",
|
|
429
|
+
supportEmail = "support@wopr.bot",
|
|
430
|
+
): TemplateResult {
|
|
413
431
|
const escapedEmail = escapeHtml(email);
|
|
414
432
|
|
|
415
433
|
const parts = [
|
|
@@ -419,10 +437,10 @@ export function dataDeletedTemplate(email: string, creditsUrl?: string): Templat
|
|
|
419
437
|
<p>You can create a new bot anytime by adding credits to your account.</p>`),
|
|
420
438
|
];
|
|
421
439
|
if (creditsUrl) parts.push(button(creditsUrl, "Add Credits"));
|
|
422
|
-
parts.push(footer(
|
|
440
|
+
parts.push(footer(`If you have questions, contact ${escapeHtml(supportEmail)}.`));
|
|
423
441
|
parts.push(unsubscribeFooter(creditsUrl ? buildUnsubscribeUrl(creditsUrl) : undefined));
|
|
424
442
|
|
|
425
|
-
const html = wrapHtml("Data Deleted", parts.join("\n"));
|
|
443
|
+
const html = wrapHtml("Data Deleted", parts.join("\n"), brandName);
|
|
426
444
|
|
|
427
445
|
const text = `Your Bot Data Has Been Deleted
|
|
428
446
|
|
|
@@ -432,9 +450,9 @@ Your suspended bot data has been permanently deleted after 30 days of inactivity
|
|
|
432
450
|
|
|
433
451
|
You can create a new bot anytime by adding credits to your account.
|
|
434
452
|
${creditsUrl ? `\nAdd credits: ${creditsUrl}` : ""}
|
|
435
|
-
If you have questions, contact
|
|
453
|
+
If you have questions, contact ${supportEmail}.${unsubscribeText(creditsUrl ? buildUnsubscribeUrl(creditsUrl) : undefined)}
|
|
436
454
|
|
|
437
|
-
(c) ${new Date().getFullYear()}
|
|
455
|
+
(c) ${new Date().getFullYear()} ${brandName}. All rights reserved.`;
|
|
438
456
|
|
|
439
457
|
return { subject: "Your bot data has been deleted", html, text };
|
|
440
458
|
}
|
|
@@ -443,23 +461,25 @@ If you have questions, contact support@wopr.bot.${unsubscribeText(creditsUrl ? b
|
|
|
443
461
|
// Org Invite
|
|
444
462
|
// ---------------------------------------------------------------------------
|
|
445
463
|
|
|
446
|
-
export function orgInviteEmailTemplate(inviteUrl: string, orgName: string): TemplateResult {
|
|
464
|
+
export function orgInviteEmailTemplate(inviteUrl: string, orgName: string, brandName = "WOPR"): TemplateResult {
|
|
447
465
|
const safeOrg = escapeHtml(orgName);
|
|
448
466
|
const safeUrl = escapeHtml(inviteUrl);
|
|
467
|
+
const b = escapeHtml(brandName);
|
|
449
468
|
|
|
450
469
|
const html = wrapHtml(
|
|
451
470
|
`You're invited to join ${safeOrg}`,
|
|
452
471
|
[
|
|
453
472
|
heading(`Join ${safeOrg}`),
|
|
454
473
|
paragraph(
|
|
455
|
-
`You've been invited to join <strong>${safeOrg}</strong> on
|
|
474
|
+
`You've been invited to join <strong>${safeOrg}</strong> on ${b}. Click the button below to accept the invitation.`,
|
|
456
475
|
),
|
|
457
476
|
button(safeUrl, "Accept Invitation"),
|
|
458
477
|
footer("This invitation expires in 7 days. If you didn't expect this email, you can safely ignore it."),
|
|
459
478
|
].join("\n"),
|
|
479
|
+
brandName,
|
|
460
480
|
);
|
|
461
481
|
|
|
462
|
-
const text = `You're invited to join ${orgName} on
|
|
482
|
+
const text = `You're invited to join ${orgName} on ${brandName}.
|
|
463
483
|
|
|
464
484
|
Accept the invitation: ${inviteUrl}
|
|
465
485
|
|