Configure email domains and sender identities from the CLI.

Email Identity

AscendKit email configuration has two layers:

  • A verified sending domain
  • One or more verified sender identities on that domain

The CLI uses the same backend APIs as the portal. Domain setup, identity management, status refresh, default sender selection, and test sends all map to the /api/email/settings backend routes.

View current email settings

ascendkit email-identity settings
ascendkit email-identity settings --json

By default this prints a compact summary of the configured domain, DNS provider, default sender, and sender identities. Use --json to print the full backend payload.

Set up a custom domain

ascendkit email-identity setup-domain yourapp.com
ascendkit email-identity status
  • setup-domain creates the SES domain identity and returns the DNS records you need to add.
  • status checks the SES domain status and public DNS records together.

To remove the custom domain and reset the environment back to the AscendKit sender:

ascendkit email-identity remove-domain

Manage sender identities

List identities and refresh their SES verification state:

ascendkit email-identity list

Add a new identity:

ascendkit email-identity add [email protected] --display-name "Your App"

Update the display name for an existing identity:

ascendkit email-identity update [email protected] --display-name "New Name"

Request SES to resend inbox verification:

ascendkit email-identity resend [email protected]

Set the default sender identity:

ascendkit email-identity set-default [email protected] --display-name "Your App"

Remove an identity:

ascendkit email-identity remove [email protected]

Send a test email from a verified identity:

ascendkit email-identity test [email protected] --to [email protected]

DNS provider shortcuts

Detect the DNS provider for the configured domain and print the provider console URL:

ascendkit email-identity open-dns

You can also detect a provider for a specific domain:

ascendkit email-identity open-dns --domain yourapp.com

Email suppressions

email-suppression list shows every address currently excluded from campaign delivery in the active environment. That includes SES-style suppressions (bounce, complaint) and user opt-outs (unsubscribe).

List excluded addresses for the current environment:

ascendkit email-suppression list
ascendkit email-suppression list --reason unsubscribe
ascendkit email-suppression list --skip 0 --limit 50
FlagDescription
--reasonFilter to bounce, complaint, or unsubscribe
--skipPagination offset (default 0)
--limitNumber of rows to return (default 100, max 500)

Remove a bounce or complaint suppression entry manually:

ascendkit email-suppression remove [email protected]

remove only applies to bounce and complaint suppressions. Unsubscribed users remain excluded until they opt back in through application logic or a future resubscribe flow.

Campaigns automatically exclude all of these addresses from delivery.

Why domain verification decides everything

Transactional email either arrives or it does not, and authentication is the largest single factor. Three DNS records matter:

RecordProvesWithout it
DKIMThe message was not altered in transitFails authentication at major providers
SPFThis server may send for the domainHigher spam placement, some rejection
DMARCWhat to do when the other two failNo visibility, weaker deliverability over time

AscendKit generates the records and detects your DNS provider, automating the Cloudflare path entirely. What it cannot skip is propagation — verification is not complete until the records are visible, which is why a correct setup can still show as pending for a while.

Reputation, and why the first campaign is the risky one

Deliverability is earned per domain and per volume. A domain that sends 50 messages a day and suddenly sends 5,000 looks, to a receiver, exactly like a compromised account — and delivery degrades even with perfect DNS.

Grow volume gradually rather than launching with your largest send. This is the single most common cause of a first campaign performing far worse than the transactional email that preceded it.

Suppression protects the same reputation. Addresses that hard-bounce or file a spam complaint stop receiving mail automatically, because continuing to send to them is the fastest way to damage a domain. Suppression is separate from an explicit unsubscribe, which is why a recipient can stop receiving email without having opted out.

Troubleshooting

Verification stays pending after adding records

DNS propagation, or records added to the wrong zone — common when an apex and a subdomain are managed separately. Confirm the records resolve with dig before assuming a problem.

Email lands in spam despite passing DKIM and SPF

Authentication is necessary, not sufficient. Content and reputation also count, and a new domain has neither. Keep transactional email short and free of marketing markup — a one-line message with a single button outperforms a designed template for verification and magic-link email.

Sends work from the dashboard but not the app

Sending from your application is server-side and requires the secret key, which is never exposed to the browser. Send from a route handler or server action, never a client component.

Related

  • Templates — authoring the content that gets sent
  • Campaigns — bulk sending, where reputation matters most
  • CLI Setup — confirming which environment you are configuring

Transactional and campaign email share a reputation

They send from the same domain, so a campaign with a high complaint rate degrades delivery of your password resets. This is why the two are separated in AscendKit rather than treated as one stream, and why campaign volume should grow gradually even when transactional volume is already healthy.

If deliverability of authentication email is critical, consider a dedicated subdomain for campaigns so the reputations are scored separately. Verify it the same way, and keep transactional sending on the domain with the longer, cleaner history.