Integrations
Resend or SMTP delivery, and confirmation and reminder emails in your own words.
Cauliflower sends its own emails: booking confirmations, reschedules and cancellations for invitees, notifications for hosts, reminders, router notifications, workspace invitations and password resets. Emails go out through Resend — or any SMTP server if you prefer — and every invitee email can be rewritten in your own words.
Email is optional. Without it, Cauliflower still books meetings, and hosts with Google Calendar connected still get calendar invites sent by Google. But invitees won't get confirmations or reminders from Cauliflower, and password reset links can't be delivered.
Configure delivery
Resend (recommended)
- Create an API key at resend.com/api-keys with Sending access, and verify your sending domain in Resend.
- Paste the key under Admin → Integrations → Email, together with the sender (for example
Acme Scheduling <[email protected]>) and an optional reply-to address. Use Send test to check it.
You can also set the key with environment variables; a key saved in the admin portal takes precedence:
RESEND_API_KEY=re_...
EMAIL_FROM="Acme Scheduling <[email protected]>"Calendar attachments, reply-to addresses and tags (type, workspace) are sent with every email, and each send carries an idempotency key, so a retried job never delivers the same email twice.
SMTP
When no Resend key is configured, Cauliflower uses SMTP. Any provider that speaks SMTP works, from Postmark and Amazon SES to Google Workspace relay.
| Variable | Default | Description |
|---|---|---|
SMTP_HOST | none | Hostname of your SMTP server. Leave empty to disable SMTP. |
SMTP_PORT | 587 | Port to connect to. |
SMTP_USER | none | Username. When empty, Cauliflower connects without authentication. |
SMTP_PASSWORD | none | Password or API token for SMTP_USER. |
SMTP_SECURE | true on port 465, otherwise false | Use implicit TLS from the start of the connection. Leave it unset on port 587, where STARTTLS is negotiated automatically. |
EMAIL_FROM | Cauliflower <no-reply@your-host> | Sender address. The default uses the hostname of APP_URL. |
The SMTP connection is created once per server process, so changes take effect after a restart. To check which provider is active, open Integrations — the Email notifications card shows Sending with Resend, Sending with SMTP or Not configured. Platform admins see the same check under Admin → System.
Deliverability
Use a sender domain you control and set up SPF, DKIM and DMARC for it (Resend walks you through this when you verify a domain). Confirmation emails carry calendar attachments and links, which spam filters scrutinize more than plain text.
Customize email templates
Workspace admins can rewrite the emails invitees receive under Settings → Emails: the booking confirmation, the reschedule notice, the cancellation and the reminder. Each template has:
- Subject and heading
- Message — a few paragraphs with light Markdown:
**bold**,*italic*,[links](https://…)and lists - Button label — the main call to action (empty hides the button)
- Show meeting details — the date, time, host and location box
Every field supports the tags below. Click a tag to insert it at the cursor, and check the live preview — it uses your logo, brand color and sample values. Reset to default restores the original wording.
Under Applies to, pick All booking links for the workspace version or a single booking link to give it its own wording. You can also edit a link's emails, and switch them on or off, from the link itself under Notifications (see Meeting types). A link without its own version uses the workspace's.
| Tag | Example |
|---|---|
{{invitee}}, {{invitee_first_name}}, {{invitee_email}}, {{company}} | Jane Cooper, Jane, [email protected], Acme |
{{host}}, {{host_first_name}}, {{host_email}}, {{host_title}} | Alex Kim, Alex, [email protected], Account Executive |
{{meeting}}, {{duration}}, {{location}} | Product demo, 30 min, the video link |
{{date}}, {{time}}, {{end_time}}, {{timezone}}, {{when}} | Tuesday, March 4 · 10:30 AM · 11:00 AM · Europe/Berlin · tomorrow at 10:30 AM |
{{join_url}}, {{manage_url}}, {{reschedule_url}}, {{cancel_url}}, {{book_again_url}} | Links for the buttons and your copy |
{{answers}}, {{notes}}, {{cancel_reason}}, {{workspace}} | Form answers, notes, the cancellation reason, your workspace name |
Invitee emails show the host's photo when they have one, your logo and your brand colors. Host notifications, router notifications and account emails keep their standard wording.
Which emails are sent
Booking emails
Every booked, rescheduled or cancelled meeting sends two kinds of email, whatever the source (booking page, router, Handoff, API or MCP):
| Recipients | Subject | Contents | |
|---|---|---|---|
| Confirmation | Invitee and guests | Confirmed: Demo with Alex Kim | What, when (in the invitee's time zone), host, where; a Join meeting or View booking button; Reschedule and Cancel links. |
| Reschedule | Invitee and guests | Updated: Demo with Alex Kim | The new time and the same links. |
| Cancellation | Invitee and guests | Cancelled: Demo with Alex Kim | The original time, the reason if one was given, and a Book a new time button. |
| Host notification | Host and co-hosts | New meeting: Jane Cooper (Acme) – Demo | Invitee, company, phone, time in the host's zone, location, source (router name, Handoff, API…), who booked it, form answers and notes. |
Host notifications have matching Rescheduled: and Cancelled: versions. Invitee emails use the host as the reply-to address, and host emails use the invitee, so replying goes straight to the other person.
The Reschedule and Cancel links only appear when the meeting type allows invitees to reschedule or cancel. Both open the manage page at https://cal.example.com/booking/<uid>.
Changes made directly in Google Calendar — a host dragging the event to a new time or deleting it — update the meeting in Cauliflower without sending Cauliflower emails, because Google already notifies the attendees.
Reminders
Each meeting type has its own list of reminder emails under Reminders & messages — up to five, between 5 minutes and 7 days before the start. New meeting types start with one reminder 24 hours before. Reminders go to the invitee and guests and include the time, the location, a join button and the manage links.
Reminders are scheduled when the meeting is booked and rescheduled again when it moves:
- Reminder times that are already in the past (or less than 5 minutes away) are skipped.
- If every reminder would be skipped and the meeting is more than 90 minutes away, a single reminder goes out one hour before instead.
- A reminder is dropped if the meeting was cancelled or moved after it was scheduled.
Reminders are background jobs that run at a set time, so they need the job runner: INTERNAL_CRON=true on Docker and VMs, or the /api/cron route on Vercel. See Deploying.
Router notifications
A Notify path step emails teammates when a lead goes down that path. Recipients are the email addresses and teammates listed on the step plus, when Notify the assignee is on, the assigned rep and the lead's owner. The email goes out right after routing, except on calendar paths where the rep isn't known until the lead books, such as a flexible team: there a step with Notify the assignee on is sent when the meeting is booked, so the booked rep gets it, and it isn't sent if the lead never books.
The subject reads Jane Cooper (Acme) was routed · Enterprise. The body shows the lead, company, title and employee count from enrichment, the router, the matched path, the outcome and the assignee, with the step's custom message at the top and an Open lead button. Replying goes to the lead.
Account emails
| When | Notes | |
|---|---|---|
| Workspace invitation | An admin invites someone who doesn't have an account yet | The link expires in 14 days. People who already have an account are added to the workspace directly, without an email. |
| Password reset | Someone uses Forgot password | The link expires in one hour. |
Turning emails off
Workspace admins can switch groups of emails off under Settings → Notifications:
- Invitee confirmations — confirmation, reschedule and cancellation emails to invitees. Turning this off also stops reminders.
- Host notifications — the emails to hosts.
- Reminders — all reminder emails, regardless of what each meeting type lists.
Each booking link can also switch off any of its invitee emails and its host notifications under Notifications. Router notifications are controlled by the Notify steps themselves, and account emails can't be turned off.
Calendar attachments
Invitee confirmation and reschedule emails carry an invite.ics attachment with METHOD:REQUEST, and cancellation emails carry one with METHOD:CANCEL, so Outlook, Apple Calendar and Gmail can add, move or remove the event with one click. The event keeps the same UID for its whole life and its sequence number increases with every reschedule, so calendar apps update the existing entry instead of adding a duplicate.
The attachment is only added when the host doesn't have a Google Calendar event for the meeting. When the host has Google Calendar connected, Cauliflower creates the event in their calendar with the invitee as an attendee, and Google sends the invitation — adding an .ics as well would give the invitee two copies.
Host notifications and reminders never include an attachment. The booking confirmation screen also offers Google, Outlook and .ics buttons so invitees can add the event themselves.
Invite templates and tags
Each meeting type has a Meeting invite section that controls the event created in the host's calendar:
- Event title — the default is
{{meeting}} · {{invitee}} <> {{host}}. The rendered title is also used as the summary of.icsattachments. - Event description — leave it empty for the default (the meeting type description, then the invitee, phone, company, form answers, notes and the manage link), or write your own.
Insert tags by clicking them in the editor or typing them in double curly braces. Unknown tags render as empty text.
| Tag | Value | Example |
|---|---|---|
{{meeting}} | Meeting type name | Product demo |
{{invitee}} | Invitee full name | Jane Cooper |
{{invitee_first_name}} | Invitee first name | Jane |
{{invitee_email}} | Invitee email | [email protected] |
{{company}} | Company | Acme |
{{host}} | Host name | Alex Kim |
{{host_first_name}} | Host first name | Alex |
{{duration}} | Duration | 30 min |
{{location}} | Location or video link | https://meet.google.com/abc-defg-hij |
{{answers}} | Guest form answers, one per line | Team size: 50 |
{{notes}} | Notes, prefixed with "Notes:" | Notes: Interested in round robin |
{{manage_url}} | Reschedule and cancel page | https://cal.example.com/booking/... |
The title editor offers the first seven tags; {{location}}, {{answers}}, {{notes}} and {{manage_url}} are only filled in the description. Templates also work through the API as title_template and invite_template on booking links.
Branding
Invitee, host, reminder, router and invitation emails use the workspace name, logo and brand colors from Settings → Branding. Password reset emails are branded as Cauliflower, because they belong to the account rather than a workspace. Every email has a plain-text version alongside the HTML.
Delivery and retries
Booking emails, reminders and router notifications are sent from the background job queue, so a slow or failing email provider never slows down or breaks a booking. A failed send is retried up to six times with growing delays (30 seconds, 2 minutes, 10 minutes, 30 minutes, then 2 hours). Jobs that still fail show up under Admin → Jobs & webhooks, where a platform admin can retry them.
Invitations and password resets are sent immediately, while the request is handled.
Running without email
When neither Resend nor SMTP is configured, every email is skipped and logged as email.skipped with the recipient and subject. Everything else keeps working:
- Meetings are booked, and hosts with Google Calendar connected still get the event, with Google sending the invite to the invitee.
- Invitees still see the confirmation screen and can download the
.icsfile or open the manage page from there. - Invitations still work: after inviting someone, copy the invitation link from the dialog or from the pending invitations list under Settings → Members and send it yourself.
- Password resets don't work, because the link can only be delivered by email. If Google sign-in is configured, people can still sign in with Google using the same email address.