Calendar
Calendar is in private beta in US production (api.agentmail.to). The beta is
not available in EU production (api.agentmail.eu). Organizations without
access receive a 403 with the message Calendar access is not enabled for this organization. Email support@agentmail.to
to request access. Upgrade to the latest Python or TypeScript SDK to use the
calendar methods.
What is the Calendar?
Every Inbox has exactly one calendar. It belongs to the inbox, uses the inbox’s address as its identity, and is deleted with it. There is nothing to create: the calendar exists from the moment the inbox does.
Your agent uses the calendar in three ways:
- Schedule. Create one-off and recurring events through the API, optionally emailing standard calendar invitations to attendees.
- Receive invitations. When someone emails the inbox a calendar invitation, the event appears on the inbox’s calendar automatically. Your agent can accept or decline it.
- React in real time. AgentMail sends
calendar.event.startingandcalendar.event.endingwebhooks as each event begins and ends, so your agent can join a call, send a reminder or follow up without running its own scheduler.
Core concepts
The calendar
The calendar is addressed by its inbox: /v0/inboxes/{inbox_id}/calendar. It has one setting, timezone, the default time zone for events created without one. It starts as UTC.
If you delete an inbox and later create a new inbox with the same address, the new inbox gets a new, empty calendar. Events from the old inbox never carry over.
Events, series and dates
Every event object has a kind:
A dated ID names a date by its original start in the series’ time zone: 7c4e9b2a-…_t20261007T090000 for a timed date, or …_d20261007 for an all-day date. It never changes, even if you move that date to another time. Get, Update, Delete and Respond accept either kind of ID; List Event Instances takes the event’s UUID. See Recurring Events.
Time and time zones
Event times are wall-clock times in an IANA time zone, the same way people schedule meetings:
Responses add the matching UTC instants, start_at and end_at. These are the moments the calendar.event.starting and calendar.event.ending webhooks are due.
- Timed events use
YYYY-MM-DDTHH:mm:ss, with no offset orZ. Thetimezonedecides the offset, including daylight-saving time. - All-day events set
all_day: trueand useYYYY-MM-DD.endis the last day of the event, inclusive, so a one-day event hasstartequal toend. An all-day event starts and ends at local midnight in itstimezone. duration_modedecides what happens when a date crosses a daylight-saving change.exactkeeps the elapsed length;nominalkeeps the wall-clock end time. One-off timed events default toexact, and recurring events tonominal, so a weekly 09:00 meeting stays 09:00 to 10:00 local time all year.
Where events come from
source is api for events your agent created. The inbox is their organizer, so your agent can send invitations and cancellations for them.
source is email for events created from an invitation the inbox received. Their organizer is whoever sent the invitation. Your agent can read them, edit its own copy and respond, but only the organizer can change them for everyone. See Invitations.
Status
status is confirmed, tentative or cancelled. A cancelled event or date stays readable, but no calendar.event.starting or calendar.event.ending webhook is sent for it. The exception is a date cancelled while it is running: it still gets its calendar.event.ending. A date cancelled by deleting its dated ID is removed from the series instead, so reading it can return 404 or 410; see Cancel dates.
Two ways to list events
Two endpoints answer two different questions:
Quick start
Then subscribe a webhook to calendar.event.starting to act when the call begins. See Calendar Webhooks.
Reads, writes and consistency
Calendar writes are processed in one primary region. Reads are served from the region closest to you and can trail a write made moments earlier by a few seconds. To read your own write immediately, pass consistency=primary to Get Calendar, Get Event, Get Agenda or List Event Instances. List Events is always read in the region that serves you. Write responses always return the stored result, so you rarely need to read back.
Webhooks are sent after a change is stored, usually within seconds.
Permissions
Calendar endpoints use their own API key permissions, from calendar_read to calendar_event_delete. See Calendar permissions for what each one allows. Keys created without a permissions object have all of them.
