REST API (White-Label Email)

Use the Smailor API to integrate white-label email into your product:

  • Let your members create mailboxes on your hosted domain(s)
  • Send outbound email from verified domains
  • Protect domain and IP reputation with automatic safety checks

Messages count toward your account plan limits.

Base URL

Use your app origin:

  • https://smailor.com (production)
  • http://localhost:5173 (local development)

Authentication

Send your API key on every request:

  • Authorization: Bearer <your_key>
  • or X-API-Key: <your_key>

The full key is shown only once in Settings -> API.

White-Label Flow (Recommended)

  1. Add and verify a custom domain (DNS + DKIM/SPF/DMARC)
  2. Call GET /api/v1/domains to confirm domain status and reputation
  3. Create member mailboxes with POST /api/v1/mailboxes
  4. Send emails with POST /api/v1/send
  5. Continuously monitor bounce/complaint rates per domain

Endpoint: List Domains + Reputation

GET /api/v1/domains

Returns all custom domains in your account with:

  • Verification state (verified)
  • 30-day sends, bounces, complaints
  • Reputation status (healthy, watch, blocked)
  • Recommendation message

Example

curl "https://smailor.com/api/v1/domains" \
  -H "Authorization: Bearer sk_smailor_..."

Endpoint: Create Mailbox (White-Label)

POST /api/v1/mailboxes

Content-Type: application/json

JSON body

Field Type Required Notes
localPart string yes Mailbox local part, example john-doe
domain string yes Must be a verified custom domain in your account
displayName string no Sender display name

Example

curl -X POST "https://smailor.com/api/v1/mailboxes" \
  -H "Authorization: Bearer sk_smailor_..." \
  -H "Content-Type: application/json" \
  -d '{
    "localPart": "john-doe",
    "domain": "mailer.yourhost.com",
    "displayName": "John Doe"
  }'

Reputation Guard

Mailbox creation is automatically blocked when domain reputation is too risky:

  • blocked status => API returns 409 domain_reputation_blocked
  • Prevents large-scale onboarding on unhealthy domains
  • Helps protect IP/domain reputation for all tenants

Endpoint: Send Email

POST /api/v1/send

Content-Type: application/json

JSON body

Field Type Required Notes
to string yes Recipient email
from string yes Must be an active address on a verified custom domain
subject string yes Subject line
text string one of text/html Plain text body
html string one of text/html HTML body (sanitized server-side)

At least one of text or html must be non-empty.

Example

curl -X POST "https://smailor.com/api/v1/send" \
  -H "Authorization: Bearer sk_smailor_..." \
  -H "Content-Type: application/json" \
  -d '{
    "to": "[email protected]",
    "from": "[email protected]",
    "subject": "Welcome",
    "text": "Your mailbox is now active."
  }'

Common Errors

Status Error Meaning
400 invalid_body, domain_not_verified Validation or domain verification issue
401 unauthorized Missing or invalid API key
403 forbidden, card_not_verified Plan/billing restrictions
409 address_taken, domain_reputation_blocked Conflict or safety guard triggered
429 too_many_requests Send frequency limit hit
5xx internal_error Temporary server issue

Best Practices for Reputation Safety

  • Use double opt-in for new senders
  • Warm up new domains gradually
  • Stop onboarding when bounce/complaint rates increase
  • Separate transactional and marketing traffic per domain
  • Monitor domain-level events daily

Reply Templates (Web Session API)

These routes power the in-app template editor and ticket composer. They authenticate with the same session as the dashboard (browser cookies after login), not with Authorization: Bearer sk_… keys used for /api/v1.

Use cases: building automation around your own logged-in browser session, internal tools same-origin with Smailor, or understanding what the UI calls.

Method Path Purpose
GET /api/templates List your templates. Optional query: ?groupId= (UUID) or ?ticketId= (UUID) to scope suggestions like the ticket reply UI.
POST /api/templates Create a template (JSON body below). Max 50 templates per account.
GET /api/templates/{id} Load one template (owner only).
PATCH /api/templates/{id} Update fields (name, description, subject, body_html, body_text, is_default, group_ids).
DELETE /api/templates/{id} Delete template.
POST /api/templates/{id}/preview Body: { "ticketId": "<uuid>" } — returns rendered subject, html, text for that ticket.
POST /api/templates/{id}/use Fire-and-forget use counter (called when a template is inserted in the UI).

Create template (POST /api/templates)

Content-Type: application/json

Field Type Required Notes
name string yes Display name
description string no Short note
subject string yes Can include {{placeholders}}
body_html string yes HTML body, min length 10
body_text string no Plain text; if omitted, derived from HTML
is_default boolean no Mark as default
group_ids string[] (UUID) no Restrict template to groups; omit or empty = all groups

Placeholders

Subject and HTML may use {{variable}} tokens. Common keys: customer_name, customer_email, ticket_id, subject, group_name, sender_name, company_name, date. Unknown keys are left unchanged at render time.

Example (session required — copy your logged-in Cookie header from the browser on your own origin)

curl -X POST "https://smailor.com/api/templates" \
  -H "Content-Type: application/json" \
  -H "Cookie: " \
  -d '{
    "name": "Thanks",
    "subject": "Re: {{subject}}",
    "body_html": "

Hi {{customer_name}},

Thanks for your message.

" }'

Errors mirror other JSON APIs: 401 when not signed in, 400 for validation or template quota, 403/404 when listing with ticketId you cannot access.

See Also