# Send email from Netlify

Send transactional email from a site on Netlify (Netlify Functions, Edge Functions, or a framework's server routes) with the Groundmail API. Your code reads the API key from the `GROUNDMAIL_API_KEY` environment variable.

---

## Prerequisites

- A Groundmail account with a [verified sending domain](https://docs.groundmail.dev/domains). A subdomain such as `mail.yourdomain.com` works well.
- A site on Netlify.

---

## Connect Netlify

1. In the dashboard, open **Integrations → Netlify** and click **Connect Netlify**.
2. Netlify asks you to authorize Groundmail. Click **Authorize**.
3. Back in Groundmail, pick a site and click **Add GROUNDMAIL_API_KEY**. Groundmail creates a sending key and sets it as `GROUNDMAIL_API_KEY` on that site for every deploy context (production, deploy previews, branch deploys and local `netlify dev`). Leave **Redeploy now** on to start a production build, so the site picks it up straight away; otherwise it applies on the next deploy.

If the site already has `GROUNDMAIL_API_KEY`, Groundmail asks before replacing it. The key never appears on screen. It's listed under **API keys** as "Netlify: *site name*", where you can revoke it.

Netlify doesn't let apps limit their access to particular sites, so Groundmail only reads your site list, writes the one variable you ask for, and writes DNS records when you click Apply DNS. **Disconnect** in Groundmail forgets the connection; to remove Groundmail from your Netlify account too, go to **User settings → Applications** in Netlify. Sites you already set up keep their key.

### By hand

Create an API key under **API keys**, then in Netlify open **Site configuration → Environment variables**, add `GROUNDMAIL_API_KEY` with the key as its value, and redeploy.

---

## Set up your domain's DNS

If your sending domain uses Netlify DNS, the same connection writes its records:

1. Add the domain under **Domains**.
2. On its **DNS** tab, click **Apply DNS (Netlify)**. Groundmail adds the SPF, DKIM, DMARC and return-path records to the Netlify DNS zone, merging into an existing SPF record, then checks them.

Netlify DNS can't edit a record in place, so when a value changes Groundmail adds the new record and then removes the old one. Subdomains such as `mail.yourdomain.com` work when their parent domain's zone is on Netlify.

---

## Send an email

**Netlify Function (Node.js)**

```bash
npm install groundmail
```

```js
// netlify/functions/welcome.mjs
import { Groundmail } from 'groundmail'

const groundmail = new Groundmail(process.env.GROUNDMAIL_API_KEY)

export default async (req) => {
  const { email } = await req.json()
  await groundmail.emails.send({
    from: 'App <no-reply@mail.yourdomain.com>',
    to: email,
    subject: 'Welcome',
    html: '<p>Thanks for signing up.</p>',
  })
  return new Response('ok')
}
```

Frameworks deployed on Netlify (Next.js, Astro, SvelteKit, Remix, Nuxt) read the same variable in their server routes. See the [Node.js guide](https://docs.groundmail.dev/frameworks/node) and the [Next.js guide](https://docs.groundmail.dev/frameworks/nextjs). Any other runtime can call `POST https://api.groundmail.dev/emails` with the key: see the [API reference](https://docs.groundmail.dev/api/emails).

---

## Troubleshooting

| Problem | Fix |
|---------|-----|
| `GROUNDMAIL_API_KEY` is undefined in a function | The variable applies to new deploys. Redeploy the site. |
| `401 Unauthorized` from Groundmail | The key was revoked or replaced. Add it again from **Integrations → Netlify**. |
| `domain is not verified` | Send from an address on a domain you verified under **Domains**. |
| A `*.netlify.app` address can't be added as a sending domain | Only Netlify controls DNS for `netlify.app`. Use a domain you own. |
