Skip to content
Use caseVerification emails & login codes

Verification emails and login codes, without a mail server

Confirm new accounts and send one-time codes from your backend with one authenticated request. Sendix handles domain signing, queueing, retries to the receiving server and the delivery trail.

  • One request per code or link
  • Template variables for codes
  • Critical priority lane
  • Bounce and suppression events
email api request
ready
send-code.tsPOST /v1/emails
await fetch("https://sendix.dev/api/v1/emails", {
  method: "POST",
  headers: {
    Authorization: "Bearer " + process.env.SENDIX_API_KEY,
    "Content-Type": "application/json",
    "Idempotency-Key": "login-code-" + challenge.id,
  },
  body: JSON.stringify({
    from: "Acme <[email protected]>",
    to: [user.email],
    subject: code + " is your Acme login code",
    template_id: LOGIN_CODE_TEMPLATE_ID,
    template_data: { code, expires_in: "10 minutes" },
    priority: "critical",
  }),
});
POST /v1/emailstemplate_datacritical
Short answer

How do I send email verification or one-time login codes with Sendix?

Generate the code or signed link in your app and store only its hash, then POST it to https://sendix.dev/api/v1/emails with template_data such as {"code": "742913"}, priority "critical" and an Idempotency-Key per challenge. Keep codes short-lived and single-use, and use email.bounced and email.suppressed events to tell users when they should try a different address.

How it works

Four steps from app event to delivered email.

What your code does, what Sendix does, and where to look when something goes wrong.

  1. 01
    your app

    Issue the challenge

    Create a 6-digit code or a signed link, store its hash with an expiry, and tie it to the user or sign-up session.

  2. 02
    POST /v1/emails

    Send it

    POST /v1/emails with the template, the code in template_data and priority "critical".

  3. 03
    single use

    Verify in your app

    Compare the submitted code with the stored hash, accept it once, and limit the number of attempts.

  4. 04
    webhooks

    Handle bad addresses

    On email.bounced or email.suppressed, prompt the user to correct the address instead of resending.

Best practices

Details that keep this mail reliable.

Habits that protect deliverability and your users, whichever provider you use.

Put the code in the subject

Users can read it from the notification preview without opening the message.

Expire codes quickly

Short validity windows (minutes, not hours) limit the value of an intercepted or forwarded message.

Limit attempts and resends

Cap guesses per code and resends per address in your app; each resend should invalidate the previous code.

Give auth mail its own sender

A dedicated address such as login@ keeps security mail recognisable and separate from product or marketing mail.

Send text with html

Include the code in plain text as well, so it survives clients that block html.

Keep list consent separate

Account verification is not newsletter consent. Use Sendix audience confirmation emails for double opt-in.

Webhook events

The events worth subscribing to.

Sendix signs each webhook with X-Sendix-Signature and keeps the same events on the message at GET /v1/emails/{id}/events.

email.deliveredWhat to do with itThe receiving server accepted the code.
email.delivery_delayedWhat to do with itTemporary failure; show a “still sending” hint.
email.bouncedWhat to do with itAddress does not exist — ask the user to fix it.
email.suppressedWhat to do with itAddress previously bounced or complained.
FAQ

Frequently asked questions

Short answers to the questions teams ask while wiring this up.

What is the difference between email verification and double opt-in?

Email verification proves that a user controls the address on their account. Double opt-in records consent to receive marketing or newsletter mail. Sendix supports double opt-in through audience confirmation emails (POST /v1/audience/contacts/{id}/send-confirmation), which store the consent proof.

Can I send magic links instead of codes?

Yes. Put the signed URL in template_data and render it in the template. Treat the link like a code: single use, short-lived, and invalidated when a new one is issued.

Do I need a verified domain to send codes?

Production sending should use a domain verified in Sendix. The dashboard lists the SPF, DKIM, DMARC and bounce records to publish and can apply them automatically for Cloudflare-hosted zones.

Can I schedule a verification email?

The API accepts scheduled_for (an ISO 8601 timestamp), but verification and login mail should normally be sent immediately with priority "critical".

Free to start

Try it on the free plan, keep the same integration as you grow.

The free plan includes 1,000 emails per month. Paid plans change volume and limits, not your API calls or SMTP settings.

Ready to send your first email?

1,000 emails free every month. No credit card required. Upgrade only when you outgrow the free tier — and we will let you know when that time comes.

Managed SaaS platform · Native SMTP engine · SOC 2 in progress