Skip to main content
POST
/
api
/
email
/
domains
Create Sending Domain
curl --request POST \
  --url https://app.puffle.ai/api/email/domains \
  --header 'Authorization: Bearer <token>' \
  --header 'Content-Type: application/json' \
  --data '
{
  "domain": "<string>"
}
'
{
  "domain": {
    "id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
    "user_id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
    "domain": "<string>",
    "agentmail_domain_id": "<string>",
    "dns_records": [
      {
        "type": "<string>",
        "name": "<string>",
        "value": "<string>",
        "priority": 123
      }
    ],
    "verified_at": "2023-11-07T05:31:56Z",
    "created_at": "2023-11-07T05:31:56Z",
    "updated_at": "2023-11-07T05:31:56Z"
  }
}
CLI:
puffle email domain create --domain <domain>

Overview

Registers a new custom domain, auto-syncs the DKIM/SPF/DMARC records when Puffle can manage the DNS zone, triggers verification, and schedules the domain-verify-poller background task to converge status as DNS propagates. Sending domains unlock creating email inboxes under that domain via createEmailAccount. Until a domain is verified, no inboxes can be provisioned on it.
This operation shares the URL path /api/email/domains with the list verb. See List sending domains to enumerate domains already registered.

AI agent notes

Verification is a multi-step DNS dance. Creating a domain does not mean it is usable. The flow is:
  1. createEmailDomain — Puffle receives DKIM/SPF/DMARC records; if managed DNS is available for the zone, records are written automatically and verification is triggered.
  2. If DNS auto-sync was skipped, status stays pending — the user must add the DNS records manually, then call verifyEmailDomain (no ?poll=true) once.
  3. The domain-verify-poller background task re-checks the live domain status on an exponential-backoff schedule (10m, 20m, 40m, 80m, 160m, 320m) for up to 12 hours.
First-verifier-wins on ownership conflicts. If another user’s unverified claim exists on the same domain, creating here will drop the stale claim. If someone else has already verified the domain, you get a 409.

Authorizations

Authorization
string
header
required

Bearer authentication header of the form Bearer <token>, where <token> is your auth token.

Body

application/json

Only domain is accepted. The handler provisions the domain, auto-syncs the DKIM/SPF/DMARC records when the zone is managed by Puffle, triggers verification if DNS was synced, and schedules the domain-verify-poller background task to converge status.

domain
string
required

Apex domain or subdomain to register. Lowercased server-side. Must be a valid domain name.

Response

Domain created. status is verified if DNS was already in place, verifying if the poller has been scheduled, or pending if DNS auto-sync failed and the user must add records manually.

domain
object
required

A custom sending domain. Domains are provisioned with backing mail infrastructure, optionally auto-synced to managed DNS, and then polled via the domain-verify-poller background task until DNS propagation is confirmed.