-
Notifications
You must be signed in to change notification settings - Fork 4
Looking at the last email I received from LessWrong, it was from no-reply@lesserwrong.com and mailed by mg.lesserwrong.com. Looking at the MX records for this subdomain,
~ dig @1.1.1.1 MX mg.lesserwrong.com
; <<>> DiG 9.10.6 <<>> @1.1.1.1 MX mg.lesserwrong.com
; (1 server found)
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 57629
;; flags: qr rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 1
;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 1232
;; QUESTION SECTION:
;mg.lesserwrong.com. IN MX
;; ANSWER SECTION:
mg.lesserwrong.com. 300 IN MX 10 mxa.mailgun.org.
;; Query time: 445 msec
;; SERVER: 1.1.1.1#53(1.1.1.1)
;; WHEN: Wed Feb 09 21:07:44 AEDT 2022
;; MSG SIZE rcvd: 78
we see that the Mailgun is the mail server provider.
Looking at the code, the core email handling module is sendEmail.ts (located in packages/lesswrong/server/emails). This gets the SMTP URL from the in-database server-only settings (see this for more on settings), and uses plain SMTP to send emails (not the Mailgun API). With nodemailer handling the SMTP peculiarities.
Then the sendEmail.ts::sendEmailSmtp function is called by renderEmail.tsx:sendEmail, and is wrapped by renderEmail.tsx:wrapAndSendEmail for custom HTML rendering. This is what is actually used in the event hooks, e.g. on signup:
const verifyEmailLink = await VerifyEmailToken.generateLink(user._id);
await wrapAndSendEmail({
user,
subject: `Verify your ${forumTitleSetting.get()} email`,
body: <div>
<p>
Click here to verify your {forumTitleSetting.get()} email
</p>
<p>
<a href={verifyEmailLink}>
{verifyEmailLink}
</a>
</p>
</div>
})For our implementation, instead of using in-DB credentials I propose continuing with the method used for the MongoDB connection string: environment variables injected at deploy time. (See the docker-compose.yml and GH actions in the deployment repository.)
This will look something like the following (with proper error handling, etc.):
const transport = nodemailer.createTransport({
host: "smtp.mailgun.org",
port: 587,
secure: false,
auth: {
user: process.env.EMAIL_USER,
pass: process.env.EMAIL_PASSWORD,
}
});