Skip to content

Production

Sanam edited this page Oct 7, 2026 · 1 revision

What to set up before real traffic: DNS on the sending domain, a shared quota store when there is more than one app instance, and tracing.

DNS setup

Each provider signs mail with its own DKIM key, so each needs its own DKIM records on your sending domain. Follow the provider's domain setup page, then check the records with a DNS lookup before the first send.

  • DKIM: add every provider's records. This is what makes mail from each of them pass.
  • DMARC: publish one record, starting with p=none and a report address, then tighten it. An aligned DKIM signature is enough for DMARC to pass.
  • SPF: optional here. SPF allows 10 DNS lookups, and four or more providers' include: entries can exceed it, which makes SPF fail for everyone. With DKIM and DMARC in place, include only the providers that need SPF, or none.

Several app instances

The quota counts live in InMemoryQuotaStore by default, which is right for one instance. A restart forgets the day's count, so a restarted app may reach a provider's own limit first; the mailer then reads the provider's quota error and marks that window used up until it resets. Instances that share accounts should share a store: implement IQuotaStore (reserve, release, mark exhausted, read usage) over your database and set FreeTierMailerOptions.QuotaStore.

Observability

Add the FreeTierMail source to your tracer and the FreeTierMail meter to your meter provider. There is one freetiermail.send span per message, counters for sends and provider attempts, and gauges for quota remaining and limit. No span, tag, metric or log line carries an address, subject, body or key; a test checks that.

Clone this wiki locally