Automations
Send an email or call your webhook automatically when a subscriber is added
Overview
An automation runs a list of steps for one subscriber when its trigger fires. Use it for welcome emails, to tell your CRM about a new sign-up, or both.
Open Automations in your company sidebar, click New Automation, pick a trigger, add steps, then click Save and activate.
Automations are part of the automation workflows plan feature. Emails sent by an automation count toward your plan's monthly email quota, like any campaign.
Triggers
Subscriber added
Fires when a subscriber is added to your company, however they got there:
- created in the dashboard or through the API (including API keys)
- imported with bulk JSON or a CSV file
- signed up on your public subscribe page (see the note on double opt-in below)
- saved automatically when you send to receivers
Only for these lists (optional). Pick one or more lists to limit the automation to subscribers on those lists. With lists picked, the automation also runs when an existing subscriber is added to one of them later.
Each automation runs once per subscriber. Editing a subscriber, re-importing them, or removing and re-adding them to a list does not start it again.
An automation only runs while its status is Active. Draft and paused automations ignore new subscribers, and subscribers added while an automation was paused are not picked up when you activate it again.
Other triggers
Tag added, Email opened, Link clicked, Date based and Webhook trigger are marked Coming soon. You can save drafts with them, but they can't be activated yet.
Steps
An automation can have up to 10 steps. They run in order. If a step fails, the run stops and later steps don't run. If a step is skipped (for example, the address is suppressed), the run continues with the next step.
Send email
Sends one of your templates. By default it goes to the subscriber who triggered the automation. It can also go to fixed addresses, such as your own team.
| Setting | Required | Description |
|---|---|---|
| Send to | Yes | The subscriber who triggered this (default) or Specific addresses |
| To | With specific addresses | 1 to 5 fixed addresses |
| CC, BCC | No | Up to 5 addresses each, in either mode. Click Add CC / BCC to show them |
| Template | Yes | One of your company's templates |
| Sending configuration | No | One of your SMTP configurations. If you leave it on Company default, your most recently added configuration is used |
| Subject override | No | Replaces the template subject. Variables work here too |
| From name | No | Replaces the sender name of the sending configuration |
A step can send to at most 10 addresses in total. When it sends to the subscriber, the subscriber counts as one of them. Addresses are trimmed, lowercased and sent once each, even if you list the same address in To and CC. When the step sends to the subscriber, their own address is removed from CC and BCC.
CC addresses are visible to everyone who receives the email. BCC addresses are delivered without appearing in the email headers.
When the step sends to the subscriber and has CC or BCC, it sends two emails:
- The subscriber's own email, to the subscriber alone. It has the usual unsubscribe link, and it doesn't show the CC or BCC addresses.
- A separate copy for the CC and BCC recipients, with the same subject and content. CC addresses are visible on the copy and BCC addresses aren't. The subscriber is not on the copy.
Templates can use these variables:
| Variable | Value |
|---|---|
[[email]] | Subscriber email |
[[first_name]], [[last_name]], [[full_name]] | Subscriber name |
[[company_name]] | Your company name |
[[unsubscribe_url]], [[preferences_url]], [[view_in_browser_url]] | Links for this email |
any custom field, e.g. [[plan]] | The subscriber's extra_fields |
Variables always describe the subscriber who triggered the automation, including in emails sent to specific addresses. That makes alerts possible: send yourself "New subscriber: [[email]]".
Unsubscribe links. When the email goes to the subscriber, it gets a List-Unsubscribe header, as with campaigns. If the template doesn't contain the unsubscribe link, a footer with that link is added. Emails sent to specific addresses are internal, so they get no unsubscribe footer and no List-Unsubscribe header. In those emails, [[unsubscribe_url]] and [[preferences_url]] become #, so your team can't unsubscribe the subscriber by mistake.
Quota and limits. Every address (the subscriber, To, CC and BCC, across both emails) counts toward your monthly email quota and the sending configuration's hourly and daily limits, and each one appears in your sent email history. SentinMail checks the total before sending anything: if the quota left is smaller than the number of addresses, nothing is sent (not even the subscriber's email) and the step fails.
If the subscriber's email goes out but the CC/BCC copy fails, the step is marked as failed, and the run history shows which email was sent. If the step runs again, the subscriber's email is not sent a second time.
Skipped addresses.
- When the step sends to the subscriber, it is skipped if the subscriber's address is on your suppression list or they haven't confirmed. The CC/BCC copy is skipped too, because it never goes out on its own.
- Suppressed addresses in To, CC or BCC are removed one by one and listed in the run history. If every To address is suppressed, the step is skipped. If every CC and BCC address is suppressed, only the copy is dropped.
- In either mode, the step is skipped if the subscriber has left every list the automation is limited to.
The step fails when your monthly quota is used up or your subscription is inactive. If the sending configuration's hourly or daily limit is reached, the run waits and continues when the limit resets.
Example: welcome email plus a sign-up alert
An automation with the trigger Subscriber added and two email steps:
- Send to: the subscriber who triggered this. Template: "Welcome". The subscriber gets their welcome email, with the usual unsubscribe link.
- Send to: specific addresses. To:
founders@yourcompany.com. BCC:crm-inbox@yourcompany.com. Template: "New sign-up alert". Subject override:New subscriber: [[email]].
The alert template can show the subscriber's details:
1<p>[[first_name]] [[last_name]] ([[email]]) just signed up.</p>2<p>Plan: [[plan]]</p>In the API, the second step looks like this:
1{2 "type": "send_email",3 "config": {4 "recipient": "custom",5 "to": ["founders@yourcompany.com"],6 "bcc": ["crm-inbox@yourcompany.com"],7 "template_id": "TEMPLATE_ID",8 "subject": "New subscriber: [[email]]"9 }10}Steps saved before these options existed have no recipient field. They keep sending to the subscriber.
Webhook
Sends an HTTP POST with a JSON body to your URL.
| Setting | Required | Description |
|---|---|---|
| URL | Yes | A public http or https URL |
| Headers | No | Extra headers, for example Authorization: Bearer ... |
| Include in payload | No | Choose whether to send the subscriber's custom fields and lists. Both are sent by default |
Header values are stored encrypted. After you save them, they are never shown again (the dashboard and the API show ********). To change a value, type a new one. Host, Content-Length, Content-Type, Transfer-Encoding, Connection and other hop-by-hop headers can't be set, and neither can headers that start with X-Sentinmail-.
Delivery. Each request times out after 10 seconds. Network errors and 5xx responses are retried up to 3 times (after 1, 2 and 4 seconds). 2xx means success. Any other status fails the step straight away. SentinMail reads at most 64 KB of your response and keeps the first 500 characters in the run history.
Payload
1{2 "event": "subscriber_added",3 "automation": { "id": "7b1e...", "name": "Welcome series" },4 "subscriber": {5 "id": "3f2a...",6 "email": "jane@example.com",7 "first_name": "Jane",8 "last_name": "Doe",9 "extra_fields": { "plan": "pro" },10 "lists": [{ "id": "9c4d...", "name": "Newsletter" }]11 },12 "company": { "id": "51e0..." },13 "sent_at": "2026-10-17T09:30:00.123456Z"14}Request headers
| Header | Value |
|---|---|
Content-Type | application/json |
User-Agent | SentinMail-Webhook/1.0 |
X-Sentinmail-Event | subscriber_added |
X-Sentinmail-Delivery | <run id>.<step index>. It stays the same across retries, so you can use it to drop duplicates |
X-Sentinmail-Signature | sha256=<hex HMAC-SHA256 of the raw body> |
Verify the signature
Each automation has its own signing secret (it starts with whsec_). It is shown once when you create the automation. Later, open the automation's Steps tab and click Reveal to see it. Rotate replaces it, and after that, requests signed with the old secret no longer verify.
Compute the HMAC over the raw request body exactly as it arrived (don't parse and re-serialize the JSON first), then compare it to the header in constant time.
1import hashlib2import hmac3 4def is_valid(raw_body: bytes, signature_header: str, secret: str) -> bool:5 expected = 'sha256=' + hmac.new(secret.encode(), raw_body, hashlib.sha256).hexdigest()6 return hmac.compare_digest(expected, signature_header or '')7 8# Django: is_valid(request.body, request.headers.get('X-Sentinmail-Signature'), SECRET)1const crypto = require('crypto');2 3// Use express.raw({ type: 'application/json' }) so req.body is a Buffer.4function isValid(rawBody, signatureHeader, secret) {5 const expected = 'sha256=' + crypto.createHmac('sha256', secret).update(rawBody).digest('hex');6 const a = Buffer.from(expected);7 const b = Buffer.from(signatureHeader || '');8 return a.length === b.length && crypto.timingSafeEqual(a, b);9}Activation checks
When you activate an automation, SentinMail checks that:
- the trigger is available (not Coming soon)
- there is at least one step
- every email step has a template from your company, and a sending configuration (either one you picked or your company default)
- every email step that sends to specific addresses has at least one To address, and all addresses are valid and within the limits
- every webhook step has a public URL and valid headers
- the selected lists belong to your company
If any check fails, the automation stays inactive and the errors appear next to the fields that need fixing. The same checks run when you save changes to an automation that is already active.
Run history
Open an automation and go to the Runs tab, or click the history icon in the automations list. Each run shows the subscriber, its status and when it ran. Click a run to see the result of each step:
| Run status | Meaning |
|---|---|
pending | Waiting to start, or waiting for a sending limit to reset |
running | Steps are being processed |
completed | Every step finished (some may have been skipped) |
failed | A step failed. The error tells you which one and why |
skipped | The run didn't start, for example because the automation was paused before it ran |
For email steps, the result lists each email the step sent (the subscriber's email and the CC/BCC copy, or the email to specific addresses) with its recipients and status, any suppressed addresses that were removed, and the Message-ID. For webhook steps, it shows the HTTP status, how many attempts were made, and the start of your response.
Run history is also available from the API, newest first and paginated:
1curl "https://api.sentinmail.app/api/emails/automations/AUTOMATION_ID/runs/?company=COMPANY_ID&page=1" \2 -H "Authorization: Bearer YOUR_ACCESS_TOKEN"