From b00814a8c46efcaff0cd6f310aa8414ed2b01886 Mon Sep 17 00:00:00 2001
From: mantikoros <95266179+mantikoros@users.noreply.github.com>
Date: Wed, 11 May 2022 10:51:58 -0500
Subject: [PATCH] Template emails (#185)
* unsubscribe from generic emails
* new welcome email
* fix from address
* thank you email
* one week bonus email
---
common/user.ts | 1 +
functions/src/email-templates/one-week.html | 519 ++++++++++++
functions/src/email-templates/thank-you.html | 463 +++++++++++
functions/src/email-templates/welcome.html | 809 +++++++++++++++++++
functions/src/emails.ts | 90 ++-
functions/src/stripe.ts | 12 +-
functions/src/unsubscribe.ts | 75 +-
7 files changed, 1924 insertions(+), 45 deletions(-)
create mode 100644 functions/src/email-templates/one-week.html
create mode 100644 functions/src/email-templates/thank-you.html
create mode 100644 functions/src/email-templates/welcome.html
diff --git a/common/user.ts b/common/user.ts
index 8f8e6d0d..dcbe28e9 100644
--- a/common/user.ts
+++ b/common/user.ts
@@ -30,6 +30,7 @@ export type PrivateUser = {
unsubscribedFromResolutionEmails?: boolean
unsubscribedFromCommentEmails?: boolean
unsubscribedFromAnswerEmails?: boolean
+ unsubscribedFromGenericEmails?: boolean
initialDeviceToken?: string
initialIpAddress?: string
}
diff --git a/functions/src/email-templates/one-week.html b/functions/src/email-templates/one-week.html
new file mode 100644
index 00000000..94889772
--- /dev/null
+++ b/functions/src/email-templates/one-week.html
@@ -0,0 +1,519 @@
+
+
+
+ 7th Day Anniversary Gift!
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ |
+
+
+
+ |
+
+
+
+
+
+ Hopefully you haven't gambled all your M$
+ away already... but if you have I bring good
+ news! Click the link below to recieve a one time
+ gift of M$ 500 to your account!
+
+
+ |
+
+
+
+
+
+
+
+
+
+ << /td>
+ |
+
+
+
+ |
+
+
+
+
+
+ If you are still engaging with our markets then
+ at this point you might as well join our Discord server.
+ You can always leave if you dont like it but
+ I'd be willing to make a market betting
+ you'll stay.
+
+
+
+
+ Cheers,
+
+
+ David from Manifold
+
+
+
+ |
+
+
+
+
+
+ |
+
+
+
+
+
+
+
+
+
+
diff --git a/functions/src/email-templates/thank-you.html b/functions/src/email-templates/thank-you.html
new file mode 100644
index 00000000..e6217334
--- /dev/null
+++ b/functions/src/email-templates/thank-you.html
@@ -0,0 +1,463 @@
+
+
+
+ Thank You for Purchasing M$
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ |
+
+
+
+ |
+
+
+
+
+
+ |
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Thank you so much for purchasing Manifold
+ Dollars! Best of luck with you forecasting!
+
+
+
+
+ Cheers,
+
+
+ David from Manifold
+
+
+
+ |
+
+
+
+
+
+ |
+
+
+
+
+
+
+
+
+
diff --git a/functions/src/email-templates/welcome.html b/functions/src/email-templates/welcome.html
new file mode 100644
index 00000000..e917147e
--- /dev/null
+++ b/functions/src/email-templates/welcome.html
@@ -0,0 +1,809 @@
+
+
+
+ Welcome to Manifold Markets
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ |
+
+
+
+ |
+
+
+
+
+
+ |
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Hi {{name}}, thanks for joining Manifold
+ Markets!
We can't wait to see what markets you will
+ create!
+
+
+ As a gift, M$1,000 has been credited to your
+ account.
+
+
+ Click the buttons to see what you can do with
+ it!
+
+
+ |
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ |
+
+
+
+ |
+
+
+
+
+
+
+
+
+
+
+ |
+
+
+
+ |
+
+
+
+
+
+
+
+
+
+
+ |
+
+
+
+ |
+
+
+
+
+
+ |
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ If you have any questions or feedback we'd
+ love to hear from you in our Discord server!
+
+
+
+
+ Looking forward to seeing you,
+
+
+ David from Manifold
+
+
+
+ |
+
+
+
+
+
+ |
+
+
+
+
+
+
+
+
+
+
diff --git a/functions/src/emails.ts b/functions/src/emails.ts
index 62825857..2b13495a 100644
--- a/functions/src/emails.ts
+++ b/functions/src/emails.ts
@@ -9,7 +9,8 @@ import { Contract, FreeResponseContract } from 'common/contract'
import { DPM_CREATOR_FEE } from 'common/fees'
import { PrivateUser, User } from 'common/user'
import { formatMoney, formatPercent } from 'common/util/format'
-import { sendTemplateEmail, sendTextEmail } from './send-email'
+
+import { sendTemplateEmail } from './send-email'
import { getPrivateUser, getUser } from './utils'
export const sendMarketResolutionEmail = async (
@@ -115,22 +116,89 @@ export const sendWelcomeEmail = async (
user: User,
privateUser: PrivateUser
) => {
- const firstName = user.name.split(' ')[0]
+ if (!privateUser || !privateUser.email) return
- await sendTextEmail(
- privateUser.email || '',
+ const { name, id: userId } = user
+ const firstName = name.split(' ')[0]
+
+ const emailType = 'generic'
+ const unsubscribeLink = `https://us-central1-${PROJECT_ID}.cloudfunctions.net/unsubscribe?id=${userId}&type=${emailType}`
+
+ await sendTemplateEmail(
+ privateUser.email,
'Welcome to Manifold Markets!',
- `Hi ${firstName},
+ 'welcome',
+ {
+ name: firstName,
+ unsubscribeLink,
+ },
+ {
+ from: 'David from Manifold ',
+ }
+ )
+}
-Thanks for joining us! We can't wait to see what markets you create.
+// TODO: use manalinks to give out M$500
+export const sendOneWeekBonusEmail = async (
+ user: User,
+ privateUser: PrivateUser
+) => {
+ if (
+ !privateUser ||
+ !privateUser.email ||
+ privateUser.unsubscribedFromGenericEmails
+ )
+ return
-Questions? Feedback? I'd love to hear from you - just reply to this email!
+ const { name, id: userId } = user
+ const firstName = name.split(' ')[0]
-Or come chat with us on Discord: https://discord.gg/eHQBNBqXuh
+ const emailType = 'generic'
+ const unsubscribeLink = `https://us-central1-${PROJECT_ID}.cloudfunctions.net/unsubscribe?id=${userId}&type=${emailType}`
-Best,
-Austin from Manifold
-https://${DOMAIN}/`
+ await sendTemplateEmail(
+ privateUser.email,
+ 'Manifold one week anniversary gift',
+ 'one-week',
+ {
+ name: firstName,
+ unsubscribeLink,
+ manalink: '', // TODO
+ },
+ {
+ from: 'David from Manifold ',
+ }
+ )
+}
+
+export const sendThankYouEmail = async (
+ user: User,
+ privateUser: PrivateUser
+) => {
+ if (
+ !privateUser ||
+ !privateUser.email ||
+ privateUser.unsubscribedFromGenericEmails
+ )
+ return
+
+ const { name, id: userId } = user
+ const firstName = name.split(' ')[0]
+
+ const emailType = 'generic'
+ const unsubscribeLink = `https://us-central1-${PROJECT_ID}.cloudfunctions.net/unsubscribe?id=${userId}&type=${emailType}`
+
+ await sendTemplateEmail(
+ privateUser.email,
+ 'Thanks for your Manifold purchase',
+ 'thank-you',
+ {
+ name: firstName,
+ unsubscribeLink,
+ },
+ {
+ from: 'David from Manifold ',
+ }
)
}
diff --git a/functions/src/stripe.ts b/functions/src/stripe.ts
index eef9f40f..c428ca88 100644
--- a/functions/src/stripe.ts
+++ b/functions/src/stripe.ts
@@ -2,7 +2,8 @@ import * as functions from 'firebase-functions'
import * as admin from 'firebase-admin'
import Stripe from 'stripe'
-import { isProd, payUser } from './utils'
+import { getPrivateUser, getUser, isProd, payUser } from './utils'
+import { sendThankYouEmail } from './emails'
export type StripeTransaction = {
userId: string
@@ -129,8 +130,15 @@ const issueMoneys = async (session: any) => {
await firestore.collection('stripe-transactions').add(transaction)
await payUser(userId, payout, true)
-
console.log('user', userId, 'paid M$', payout)
+
+ const user = await getUser(userId)
+ if (!user) return
+
+ const privateUser = await getPrivateUser(userId)
+ if (!privateUser) return
+
+ await sendThankYouEmail(user, privateUser)
}
const firestore = admin.firestore()
diff --git a/functions/src/unsubscribe.ts b/functions/src/unsubscribe.ts
index 7c9442d7..c2981358 100644
--- a/functions/src/unsubscribe.ts
+++ b/functions/src/unsubscribe.ts
@@ -15,46 +15,57 @@ export const unsubscribe = functions
if (type === 'market-resolved') type = 'market-resolve'
- if (!['market-resolve', 'market-comment', 'market-answer'].includes(type)) {
+ if (
+ ![
+ 'market-resolve',
+ 'market-comment',
+ 'market-answer',
+ 'generic',
+ ].includes(type)
+ ) {
res.status(400).send('Invalid type parameter.')
return
}
const user = await getUser(id)
- if (user) {
- const { name } = user
-
- const update: Partial = {
- ...(type === 'market-resolve' && {
- unsubscribedFromResolutionEmails: true,
- }),
- ...(type === 'market-comment' && {
- unsubscribedFromCommentEmails: true,
- }),
- ...(type === 'market-answer' && {
- unsubscribedFromAnswerEmails: true,
- }),
- }
-
- await firestore.collection('private-users').doc(id).update(update)
-
- if (type === 'market-resolve')
- res.send(
- `${name}, you have been unsubscribed from market resolution emails on Manifold Markets.`
- )
- else if (type === 'market-comment')
- res.send(
- `${name}, you have been unsubscribed from market comment emails on Manifold Markets.`
- )
- else if (type === 'market-answer')
- res.send(
- `${name}, you have been unsubscribed from market answer emails on Manifold Markets.`
- )
- else res.send(`${name}, you have been unsubscribed.`)
- } else {
+ if (!user) {
res.send('This user is not currently subscribed or does not exist.')
+ return
}
+
+ const { name } = user
+
+ const update: Partial = {
+ ...(type === 'market-resolve' && {
+ unsubscribedFromResolutionEmails: true,
+ }),
+ ...(type === 'market-comment' && {
+ unsubscribedFromCommentEmails: true,
+ }),
+ ...(type === 'market-answer' && {
+ unsubscribedFromAnswerEmails: true,
+ }),
+ ...(type === 'generic' && {
+ unsubscribedFromGenericEmails: true,
+ }),
+ }
+
+ await firestore.collection('private-users').doc(id).update(update)
+
+ if (type === 'market-resolve')
+ res.send(
+ `${name}, you have been unsubscribed from market resolution emails on Manifold Markets.`
+ )
+ else if (type === 'market-comment')
+ res.send(
+ `${name}, you have been unsubscribed from market comment emails on Manifold Markets.`
+ )
+ else if (type === 'market-answer')
+ res.send(
+ `${name}, you have been unsubscribed from market answer emails on Manifold Markets.`
+ )
+ else res.send(`${name}, you have been unsubscribed.`)
})
const firestore = admin.firestore()