Reference: Events (V1) Endpoint Documentation
Events represent non-patient schedule blocks on the office calendar — team meetings, training sessions, closures, and similar items. They are distinct from AppointmentV1 records, which are tied to patients and clinical workflows.
All Events V1 endpoints require an Organization-ID header. Read operations require the model:read scope; write operations (POST, PUT, DELETE) require model:write.
⚠️ Rate Limited: Events endpoints are rate limited. See the rate limiting guide for details.
Returns a paginated list of events matching the provided filter criteria.
| Parameter | In | Required | Type | Description |
|---|---|---|---|---|
Organization-ID | header | Yes | string | Your organization identifier |
filter | query | No | string | Filter expression. See Filter Keys below |
responseFields | query | No | string | URL-encoded comma-delimited list of fields to return. Use ALL for all fields |
page | query | No | string | Page number for offset-based pagination |
pageSize | query | No | string | Number of records per page |
lastId | query | No | string | The largest eventId from the previous page — used for cursor-based pagination |
| Filter Key | Supported Operators |
|---|---|
id | -> |
title | ==, !=, ~=, <>= |
start | >, >=, <, <= |
operatory.id | ==, !=, -> |
location.id | ==, !=, -> |
provider.id | ==, !=, -> |
lastModified | >, >=, <, <= |
groupId | == |
Upcoming Breaking Change:
location.id(as a list of IDs or["ALL"]) will become a required filter. Omitting it currently defaults to all locations. See Location-Based API Billing.
Date-limiting filter: If you do not provide a date-limiting filter (
lastModified,start, orcreatedDate), the server may automatically applylastModified >=your organization's creation date or one year ago — whichever is more recent.
Ordering: When filtering by
startorlastModified, results are returned in descending order (newest first). UselastIdwith date filters for stable pagination.
Fetch events modified after a date at a specific location:
GET /api/v1/events?filter=lastModified>=2025-01-01T00:00:00Z,location.id->[64000000000004]Fetch events for a provider within a date range:
GET /api/v1/events?filter=start>=2025-06-01,start<=2025-06-30,provider.id==789Paginate using lastId:
GET /api/v1/events?lastId=9000000903375&pageSize=100&filter=lastModified>=2025-01-01T00:00:00Z,location.id->[64000000000004]Returns a single event by its ID.
| Parameter | In | Required | Type | Description |
|---|---|---|---|---|
eventId | path | Yes | integer | The ID of the event |
Organization-ID | header | Yes | string | Your organization identifier |
responseFields | query | No | string | Comma-delimited list of fields to return, or ALL |
GET /api/v1/events/9000000903375GET /api/v1/events/async retrieves events asynchronously. It returns the first 10 matching results immediately in the HTTP response and streams all matching records to the Streaming API.
See the Async Endpoints V1 — Developer Guide for shared async mechanics, parameters, and pagination. Filter keys are the same as bulk list above.
Returns the total number of events matching a filter. Uses the same filter syntax as GET /v1/events.
| Parameter | In | Required | Type | Description |
|---|---|---|---|---|
Organization-ID | header | Yes | string | Your organization identifier |
filter | query | No | string | Filter criteria — same keys as bulk GET |
GET /api/v1/events/totalcount?filter=lastModified>=2025-01-01,location.id==123| Field | Type | Description |
|---|---|---|
data.total | integer | Number of events matching the filter |
Creates a new event. Supports one-time and recurring events (WEEKLY or MONTHLY patterns).
| Parameter | In | Required | Type | Description |
|---|---|---|---|---|
Organization-ID | header | Yes | string | Your organization identifier |
Required fields:
| Field | Type | Description |
|---|---|---|
title | string | Event title (max 60 characters) |
start | string (date-time) | Start time in ISO 8601 format (e.g. 2025-01-15T10:00:00.000Z) |
location | object | Linked model { "id": "<locationId>" } |
Optional fields:
| Field | Type | Default | Description |
|---|---|---|---|
duration | integer | 60 | Length in minutes. Valid range: 5–1440 |
description | string | — | Free-text description |
allDay | boolean | — | When true, start is normalized to location midnight and duration is set to 1439 minutes |
color | string | bbbbbb | 6-character hexadecimal color code without # prefix (e.g. FF5733) |
operatory | object | — | Linked model { "id": "<operatoryId>" }. Must belong to the same location |
provider | object | — | Linked model { "id": "<providerId>" }. Must be active with isNonPersonEntity: false |
Recurrence fields (all required together when creating a recurring series):
| Field | Type | Notes |
|---|---|---|
recurrenceType | string | WEEKLY or MONTHLY |
recurrenceStart | string (date) | Start of recurrence range (YYYY-MM-DD) |
recurrenceEnd | string (date) | End of recurrence range. Max 2 years after recurrenceStart |
recurrenceFrequency | integer | Interval (1–52) |
recurrenceDays | array | Required for WEEKLY. Values: SUNDAY–SATURDAY |
recurrenceWeek | string | Required for MONTHLY. Values: FIRST, SECOND, THIRD, FOURTH, LAST |
recurrenceDay | string | Required for MONTHLY. Day of week (SUNDAY–SATURDAY) |
POST /api/v1/events
Content-Type: application/json
{
"title": "Team Meeting",
"start": "2025-01-15T10:00:00.000Z",
"duration": 60,
"location": { "id": "64000000000004" },
"operatory": { "id": "9000000000338" },
"color": "FF5733"
}POST /api/v1/events
Content-Type: application/json
{
"title": "Weekly Standup",
"start": "2025-01-15T10:00:00.000Z",
"duration": 30,
"location": { "id": "64000000000004" },
"recurrenceType": "WEEKLY",
"recurrenceStart": "2025-01-15",
"recurrenceEnd": "2025-06-15",
"recurrenceFrequency": 1,
"recurrenceDays": ["MONDAY", "WEDNESDAY", "FRIDAY"]
}Returns 201 Created with the created EventV1 in data.
Updates an existing event. The request body uses the EventV1 model with partial update semantics: only properties present in the JSON body are changed; omitted properties are left unchanged.
| Parameter | In | Required | Type | Description |
|---|---|---|---|---|
eventId | path | Yes | integer | The ID of the event to update |
Organization-ID | header | Yes | string | Your organization identifier |
recurrenceTarget | query | Yes | string | SERIES or OCCURRENCE (uppercase only) |
responseFields | query | No | string | Comma-delimited list of fields to return, or ALL |
| Value | Behavior |
|---|---|
OCCURRENCE | Updates only the single event identified by eventId |
SERIES | Updates the recurring series (required when modifying recurrence settings; propagates time changes across future occurrences) |
Note: Although the
EventV1schema liststitle,start, andlocationas required for create, none of these are required on PUT. Send only the fields you want to change.
| Property | Notes |
|---|---|
title | string, max 60 characters |
description | string; send null to clear |
start | ISO 8601 date-time |
duration | integer, 5–1440 minutes; recomputes end |
allDay | boolean; when true, duration is forced to 1439 min and start is normalized to location midnight |
color | 6-char hex, no # prefix |
operatory | linked model { id }; send null to clear |
provider | linked model { id }; send null to clear |
recurrenceType, recurrenceStart, recurrenceEnd, recurrenceFrequency | require recurrenceTarget=SERIES |
recurrenceDays | required for WEEKLY recurrence updates |
recurrenceWeek, recurrenceDay | required for MONTHLY recurrence updates |
| Property | Behavior |
|---|---|
location | Read-only after create — if sent, a warning is returned and the value is ignored |
end | Read-only — computed from start + duration; sending end has no effect |
id, lastModified, groupId, type | Read-only response fields |
PUT /api/v1/events/9000000903375?recurrenceTarget=OCCURRENCE
Content-Type: application/json
{
"title": "Updated Team Meeting",
"duration": 90
}Returns 200 OK with the updated EventV1 in data.
Deletes an event by ID.
| Parameter | In | Required | Type | Description |
|---|---|---|---|---|
eventId | path | Yes | integer | The ID of the event to delete |
Organization-ID | header | Yes | string | Your organization identifier |
recurrenceTarget | query | Conditional | string | Required when the event is part of a recurring series. SERIES or OCCURRENCE |
recurrenceTarget | Behavior |
|---|---|
OCCURRENCE | Deletes only the single occurrence |
SERIES | Deletes the target occurrence and all future occurrences in the series |
Delete a one-time event:
DELETE /api/v1/events/9000000903375Delete a single occurrence from a recurring series:
DELETE /api/v1/events/9000000903375?recurrenceTarget=OCCURRENCEReturns 200 OK with { "data": { "id": <eventId> } }.
A successful response returns the following top-level structure:
| Field | Type | Description |
|---|---|---|
data | object or array | The event object (single) or array of events (bulk) |
warnings | array | Non-fatal warnings (operation still succeeded) |
errors | array | Field-level or structural errors |
For bulk responses, data is an array and the response also includes meta.pagination with lastId for cursor pagination.
| Field | Access | Description |
|---|---|---|
id | read-only | Unique event identifier |
type | read-only | Always "EventV1" |
title | read/write | Event title (max 60 characters) |
description | read/write | Free-text description |
start | read/write | Start time (ISO 8601) |
end | read-only | Computed from start + duration |
duration | read/write | Length in minutes (5–1440) |
allDay | read/write | All-day event flag |
color | read/write | 6-char hex color (defaults to bbbbbb) |
lastModified | read-only | Last modification timestamp |
groupId | read-only | Group identifier for recurring events (max 50 chars) |
location | read/write on create; read-only on update | Linked model { id } |
operatory | read/write | Linked model { id }; optional |
provider | read/write | Linked model { id }; optional |
recurrenceType | read/write | WEEKLY or MONTHLY; null for non-recurring |
recurrenceStart | read/write | Recurrence range start (YYYY-MM-DD) |
recurrenceEnd | read/write | Recurrence range end (YYYY-MM-DD) |
recurrenceFrequency | read/write | Recurrence interval (1–52) |
recurrenceDays | read/write | Days of week for WEEKLY recurrence |
recurrenceWeek | read/write | Week of month for MONTHLY recurrence |
recurrenceDay | read/write | Day of week for MONTHLY recurrence |
lastId is the recommended approach for iterating through large result sets. It uses the event's id as a cursor rather than an offset.
GET /api/v1/events?pageSize=100&filter=lastModified>=2025-01-01T00:00:00Z,location.id->[64000000000004]Pass the id of the last record in data as lastId:
GET /api/v1/events?lastId=9000000903375&pageSize=100&filter=lastModified>=2025-01-01T00:00:00Z,location.id->[64000000000004]Continue until data is empty.
⚠️ Not Recommended: Do not paginate large data sets using the
pageparameter. UselastIdinstead.
Events are streamable via the Streaming API. Create, update, and delete operations emit stream messages. The async bulk GET endpoint also delivers matching records to the Streaming API.
See the Streaming API Webhooks Setup Guide for setup instructions.
organizationId.locationId.EventV1.operationTypeAll event changes at a specific location:
66d22762060811049b50d085.64000000000004.EventV1.*All CREATE events across all locations:
66d22762060811049b50d085.*.EventV1.CREATE| Operation | When |
|---|---|
CREATE | A new event (or recurring series) is created |
UPDATE | An event or series occurrence is updated |
DELETE | An event or series occurrence is deleted |
HTTP Status Code Errors — click to expand
These apply to all Events V1 endpoints.
The request body or query parameters are invalid or cannot be processed. See Field-Level Validation Errors below.
| Message | Authentication is required and has failed or has not been provided. |
| Why | Missing, expired, or malformed Bearer token. |
| Fix | Provide a valid Bearer token in the Authorization header. |
| Message | The request is understood, but it has been refused or access is not allowed. |
| Why | The token lacks the required scope. Read operations require model:read; write operations require model:write. |
| Fix | Request a token with the appropriate scope. |
| Message | The requested resource is either missing or does not exist. |
| Why | No event exists for the given eventId within your organization, or the ID is invalid. |
| Fix | Confirm the eventId is correct and belongs to your organization. |
| Message | The server timed out while processing the request. |
| Why | High server load or an overly broad filter. |
| Fix | Narrow filter criteria and retry. |
| Message | Rate limit exceeded. |
| Why | Too many requests in a short period. |
| Fix | Implement exponential backoff. See the rate limiting guide. |
| Message | An unexpected error occurred. |
| Fix | Retry. If the issue persists, contact support with the request details and timestamp. |
Field-Level Validation Errors — click to collapse
Error: title must be longer than or equal to 1 characters / title must be a string
| Why | title was omitted, empty, or not a string. |
| Fix | Provide a non-empty string up to 60 characters. |
Error: 'undefined' is not a valid date in the format 'YYYY-MM-DD[T]HH:mm:ss.SSS[Z]'.
| Why | start was omitted or not a valid ISO 8601 date-time. |
| Fix | Provide a valid date-time, e.g. 2025-01-15T10:00:00.000Z. |
Error: start and end should be at the same day
| Why | For non-allDay events, the computed end time falls on a different calendar day than start (in the location's timezone). |
| Fix | Adjust start or duration so the event fits within a single day. |
Error: duration must be an integer between 5 and 1440.
| Why | Duration is outside the allowed range. |
| Fix | Provide a value between 5 and 1440 inclusive. |
Error: Linked model for property 'location' should be plain object with id of LocationV1
| Why | location was omitted on create or not a valid linked model. |
| Fix | Provide { "id": "<locationId>" } with a valid location ID. |
Warning: Property 'location' is read-only. Assignment is ignored.
| Why | location was included in a PUT request body. |
| Fix | Omit location from update requests. Location cannot be changed after create. |
Error: Location of Event and Location of Operatory should be the same
| Why | The operatory belongs to a different location than the event. |
| Fix | Assign an operatory at the same location as the event. |
Error: Provider should have 'isNonPersonEntity: false' to be assigned to the appointment
| Why | The provider is a non-person entity. |
| Fix | Assign a person provider. |
Error: Provider should have 'active: true' to be assigned to the appointment
| Why | The provider is inactive. |
| Fix | Use an active provider or reactivate the provider first. |
Error: color must be a 6-character hexadecimal color code without # prefix
| Why | Invalid color format (e.g. includes #, wrong length, non-hex characters). |
| Fix | Use exactly 6 hex characters, e.g. FF5733 or aabbcc. |
Error: recurrenceTarget must have a value in [SERIES,OCCURRENCE]
| Why | recurrenceTarget was omitted on PUT, or an invalid value was provided (including lowercase). |
| Fix | Provide recurrenceTarget=SERIES or recurrenceTarget=OCCURRENCE in uppercase. |
Error: recurrenceTarget should be SERIES if fields for modifying recurrence settings are provided
| Why | Recurrence fields were sent in the body with recurrenceTarget=OCCURRENCE. |
| Fix | Use recurrenceTarget=SERIES when modifying recurrence settings. |
Error: recurrenceTarget cannot be SERIES because event doesn't have recurrence settings
| Why | recurrenceTarget=SERIES was used on DELETE for a non-recurring event. |
| Fix | Omit recurrenceTarget for one-time events, or use OCCURRENCE. |
Error: recurrenceStart cannot be after the recurrenceEnd
| Fix | Ensure recurrenceStart is on or before recurrenceEnd. |
Error: range between recurrenceStart and recurrenceEnd cannot be bigger than 2 years
| Fix | Limit the recurrence range to 2 years or less. |
Error: No events can be created for provided recurrence settings
| Why | The recurrence configuration produces zero event dates. |
| Fix | Adjust recurrence days, frequency, or date range so at least one occurrence is generated. |
Error: recurrenceDays should not be empty / recurrenceFrequency must not be less than 1 / recurrenceFrequency must not be greater than 52
| Why | Incomplete or out-of-range recurrence configuration. |
| Fix | Provide all required recurrence fields for the chosen recurrenceType. See POST — Create Event. |