Skip to main content

Appointments

An appointment is a calendar meeting with its attendees, stored once per user. These endpoints list and search appointments and replace their tags.

Every endpoint below shows its parameters and response fields in the middle and a request sample with an example response on the right.

Base URL https://api.sally.ioVersion v1.0 current, not frozen yetHow versioning works

Searches appointments (subject, attendee, time range), paginated​

GET/v1.0/directories/{directoryId}/appointments

Case-insensitive substring search (see „Text search" above): ?subject matches any part of the subject (start, middle or end), ?attendee any part of an attendee name/email. ?from/?to filter on StartTime and are UTC ISO-8601 (YYYY-MM-DDTHH:MM:SSZ, see „Dates & times" above). Pagination via ?page + ?pageSize (max. 100). Sorted by StartTime descending.

Field overview from the specification

Response fields:

  • page / pageSize / total / hasMore: pagination envelope (current page, page size, total count, whether more pages follow).
  • items (array): the appointments on this page. Each item has:
    • appointmentId (string): id of the appointment.
    • subject (string): subject of the appointment.
    • description (string | null): body of the appointment as delivered by the calendar; usually HTML for Outlook/Google appointments, plain text for ones created in Sally. Returned verbatim.
    • startTime (string | null): start time (ISO-8601).
    • endTime (string | null): end time (ISO-8601).
    • durationInMinutes (number | null): duration in minutes.
    • isAllDay (boolean): true if the appointment spans whole days.
    • location (string | null): location of the appointment.
    • isPrivate (boolean): true if the appointment is marked as private.
    • isCanceled (boolean): true if the appointment was canceled.
    • isRecurring (boolean): true if the appointment is part of a recurring series.
    • icalId (string | null): the iCalendar UID from the source calendar, for matching against your own copy. Not unique within a directory (one copy per synced calendar).
    • attendees (array): the attendees. Each has:
      • name (string | null): name of the attendee.
      • email (string | null): email/address entry of the attendee.
      • isRequired (boolean): true for a required participant, false for an optional one.
      • invitationStatus (string enum): invitation status; one of declined, accepted, tentative, notResponded, organizer, unknown.
      • attendanceStatus (string enum): attendance status; one of notAttended, attended, unknown.
    • tags (array): effective tags (own + inherited from the recurring series master). Each has:
      • tagId (string): id of the tag.
      • name (string): tag display name.
      • colorCode (string | null): a colour key from the Sally tag palette (a colour name like blue/red/green, not a raw hex value; full list in the schema); null if unset.

Path parameters

  • directoryIdstringrequired

    Id of the directory (the Sally company account) the resource belongs to. The directories a token can address are listed by GET /v1.0/me/directories/memberships.

Query parameters

  • pagenumberoptional

    Page number, 1-based. Defaults to 1.

  • pageSizenumberoptional

    Items per page. Defaults to 25, capped at 100.

  • subjectstringoptional

    Case-insensitive substring match on the subject. The term may appear at the start, middle, or end (e.g. "meet" matches "Weekly Meeting").

  • attendeestringoptional

    Case-insensitive substring match on an attendee name or email. The term may appear at the start, middle, or end (e.g. "ann" matches "Joanna").

  • fromstringoptional

    Only appointments with StartTime >= this UTC ISO-8601 timestamp (YYYY-MM-DDTHH:MM:SSZ).

  • tostringoptional

    Only appointments with StartTime <= this UTC ISO-8601 timestamp (YYYY-MM-DDTHH:MM:SSZ).

  • fieldsstringoptional

    Comma-separated list of the fields to return. Leave it out and you get every field — including fields added in the future, which is your call to make: name your fields if you want to be shielded from that.

    Only first-level fields can be named. A nested list such as attendees, tags or sectionItems is returned whole or not at all; attendees.name is not supported.

    On a paged response the selection applies to the entries in items; page, pageSize, total and hasMore are always returned. An unknown name is rejected with 400 rather than ignored.

    Selectable here: appointmentId, attendees, description, durationInMinutes, endTime, icalId, isAllDay, isCanceled, isPrivate, isRecurring, location, startTime, subject, tags.

    Example: appointmentId,attendees

Response: each entry in items

  • appointmentIdstringrequired

    Id of the appointment.

  • subjectstringrequired

    Subject of the appointment.

  • descriptionstringrequirednullable

    Body of the appointment as delivered by the calendar. Usually HTML for appointments that come from Outlook or Google Calendar, plain text for appointments created in Sally. Returned verbatim, so render it accordingly. Null if the appointment has no body.

  • startTimestringrequirednullable

    Start time (ISO-8601).

  • endTimestringrequirednullable

    End time (ISO-8601).

  • durationInMinutesnumberrequirednullable

    Duration in minutes.

  • isAllDaybooleanrequired

    True if the appointment spans whole days. Appointments migrated from the old system may carry no value for this, which counts as false.

  • locationstringrequirednullable

    Location of the appointment.

  • isPrivatebooleanrequired

    True if the appointment is marked as private.

  • isCanceledbooleanrequired

    True if the appointment was canceled.

  • isRecurringbooleanrequired

    True if the appointment is part of a recurring series.

  • icalIdstringrequirednullable

    The iCalendar UID of the appointment, as reported by the calendar it came from. Use it to match an appointment against your own copy of the same calendar entry. NOT unique within a directory: the same entry appears once per calendar it was synced from, and all of those copies share this value. Null for appointments that never came from a calendar.

  • attendeesobject[]required

    Attendees.

    5 child fields
    • namestringrequirednullable

      Name of the attendee.

    • emailstringrequirednullable

      Email/address entry of the attendee.

    • invitationStatusstringrequired

      Invitation status of the attendee.

      Allowed values: declinedacceptedtentativenotRespondedorganizerunknown
    • attendanceStatusstringrequired

      Attendance status of the attendee.

      Allowed values: notAttendedattendedunknown
    • isRequiredbooleanrequired

      True if the attendee is a required participant, false if optional (as set in the calendar).

  • tagsobject[]required

    Effective tags (own + inherited from the recurring series master).

    3 child fields
    • tagIdstringrequired

      Id of the tag.

    • namestringrequired

      Tag display name.

    • colorCodestringrequirednullable

      Colour of the tag as a key from Sally's fixed tag palette — a colour NAME, not a raw hex value. One of: indigo, purple, fuchsia, pink, rose, red, orange, amber, yellow, lime, green, emerald, teal, cyan, sky, blue, slate, gray, zinc, stone, neutral. The client maps the key to the actual (light/dark) colour; null or an unknown key renders in the neutral default colour. Null if unset.

Every page also carries page, pageSize, total, hasMore.

Status codes

  • 200Success
  • 400

    Invalid request (validation error).

  • 401

    Missing or invalid bearer token.

  • 404

    Resource not found or not accessible.

  • 429

    Rate limit exceeded (per token/IP). Transcription uploads may also return code FUP_LIMIT_EXCEEDED or TOO_MANY_CONCURRENT_TRANSCRIPTIONS.

  • 500

    Internal server error.

POST/v1.0/directories/{directoryId}/appointments/search

Searches appointments, sorted by StartTime descending.

Field overview from the specification

Body fields:

  • search (string, optional): case-insensitive substring over subject, description, and attendee name/email; a match in any of them counts.
  • from (string, optional): only appointments with StartTime >= this UTC ISO-8601 timestamp (YYYY-MM-DDTHH:MM:SSZ).
  • to (string, optional): only appointments with StartTime <= this UTC ISO-8601 timestamp (YYYY-MM-DDTHH:MM:SSZ).
  • page (number, optional, default 1): 1-based page number.
  • pageSize (number, optional, default 25): page size, max. 100.

Path parameters

  • directoryIdstringrequired

    Id of the directory (the Sally company account) the resource belongs to. The directories a token can address are listed by GET /v1.0/me/directories/memberships.

Query parameters

  • fieldsstringoptional

    Comma-separated list of the fields to return. Leave it out and you get every field — including fields added in the future, which is your call to make: name your fields if you want to be shielded from that.

    Only first-level fields can be named. A nested list such as attendees, tags or sectionItems is returned whole or not at all; attendees.name is not supported.

    On a paged response the selection applies to the entries in items; page, pageSize, total and hasMore are always returned. An unknown name is rejected with 400 rather than ignored.

    Selectable here: appointmentId, attendees, description, durationInMinutes, endTime, icalId, isAllDay, isCanceled, isPrivate, isRecurring, location, startTime, subject, tags.

    Example: appointmentId,attendees

Request body application/json

  • searchstringoptionalnullable

    Case-insensitive substring match over subject, description and attendee name/email. The term may appear at the start, middle, or end of any of them; a hit in any one counts.

  • fromstringoptionalnullable

    Only appointments with StartTime >= this UTC ISO-8601 timestamp (YYYY-MM-DDTHH:MM:SSZ).

  • tostringoptionalnullable

    Only appointments with StartTime <= this UTC ISO-8601 timestamp (YYYY-MM-DDTHH:MM:SSZ).

  • pagenumberoptional

    Page (1-based, default 1).

  • pageSizenumberoptional

    Page size (default 25, max 100).

Response: each entry in items

  • appointmentIdstringrequired

    Id of the appointment.

  • subjectstringrequired

    Subject of the appointment.

  • descriptionstringrequirednullable

    Body of the appointment as delivered by the calendar. Usually HTML for appointments that come from Outlook or Google Calendar, plain text for appointments created in Sally. Returned verbatim, so render it accordingly. Null if the appointment has no body.

  • startTimestringrequirednullable

    Start time (ISO-8601).

  • endTimestringrequirednullable

    End time (ISO-8601).

  • durationInMinutesnumberrequirednullable

    Duration in minutes.

  • isAllDaybooleanrequired

    True if the appointment spans whole days. Appointments migrated from the old system may carry no value for this, which counts as false.

  • locationstringrequirednullable

    Location of the appointment.

  • isPrivatebooleanrequired

    True if the appointment is marked as private.

  • isCanceledbooleanrequired

    True if the appointment was canceled.

  • isRecurringbooleanrequired

    True if the appointment is part of a recurring series.

  • icalIdstringrequirednullable

    The iCalendar UID of the appointment, as reported by the calendar it came from. Use it to match an appointment against your own copy of the same calendar entry. NOT unique within a directory: the same entry appears once per calendar it was synced from, and all of those copies share this value. Null for appointments that never came from a calendar.

  • attendeesobject[]required

    Attendees.

    5 child fields
    • namestringrequirednullable

      Name of the attendee.

    • emailstringrequirednullable

      Email/address entry of the attendee.

    • invitationStatusstringrequired

      Invitation status of the attendee.

      Allowed values: declinedacceptedtentativenotRespondedorganizerunknown
    • attendanceStatusstringrequired

      Attendance status of the attendee.

      Allowed values: notAttendedattendedunknown
    • isRequiredbooleanrequired

      True if the attendee is a required participant, false if optional (as set in the calendar).

  • tagsobject[]required

    Effective tags (own + inherited from the recurring series master).

    3 child fields
    • tagIdstringrequired

      Id of the tag.

    • namestringrequired

      Tag display name.

    • colorCodestringrequirednullable

      Colour of the tag as a key from Sally's fixed tag palette — a colour NAME, not a raw hex value. One of: indigo, purple, fuchsia, pink, rose, red, orange, amber, yellow, lime, green, emerald, teal, cyan, sky, blue, slate, gray, zinc, stone, neutral. The client maps the key to the actual (light/dark) colour; null or an unknown key renders in the neutral default colour. Null if unset.

Every page also carries page, pageSize, total, hasMore.

Status codes

  • 200Success
  • 400

    Invalid request (validation error).

  • 401

    Missing or invalid bearer token.

  • 403

    Forbidden (insufficient permissions).

  • 404

    Resource not found or not accessible.

  • 429

    Rate limit exceeded (per token/IP). Transcription uploads may also return code FUP_LIMIT_EXCEEDED or TOO_MANY_CONCURRENT_TRANSCRIPTIONS.

  • 500

    Internal server error.

Replaces the tags of an appointment (assign/unassign)​

PUT/v1.0/directories/{directoryId}/appointments/{appointmentId}/tags

Replace-set of the tags on an appointment. Series tags live on the recurring master and are inherited, not set here. Max. 20 tags per appointment.

Field overview from the specification

Body fields:

  • tagIds (string array): existing tag ids to assign; the given set replaces the current one. Assigning only takes tag ids, so create the tag first via POST /v1.0/directories/{directoryId}/tags and assign it here.

Path parameters

  • directoryIdstringrequired

    Id of the directory (the Sally company account) the resource belongs to. The directories a token can address are listed by GET /v1.0/me/directories/memberships.

  • appointmentIdstringrequired

    Id of the appointment.

Query parameters

  • fieldsstringoptional

    Comma-separated list of the fields to return. Leave it out and you get every field — including fields added in the future, which is your call to make: name your fields if you want to be shielded from that.

    Only first-level fields can be named. A nested list such as attendees, tags or sectionItems is returned whole or not at all; attendees.name is not supported.

    On a paged response the selection applies to the entries in items; page, pageSize, total and hasMore are always returned. An unknown name is rejected with 400 rather than ignored.

    Selectable here: colorCode, name, tagId.

    Example: colorCode,name

Request body application/json

  • tagIdsstring[]optional

    Existing tag ids to assign; the given set replaces the current one.

Response

  • tagIdstringrequired

    Id of the tag.

  • namestringrequired

    Tag display name.

  • colorCodestringrequirednullable

    Colour of the tag as a key from Sally's fixed tag palette — a colour NAME, not a raw hex value. One of: indigo, purple, fuchsia, pink, rose, red, orange, amber, yellow, lime, green, emerald, teal, cyan, sky, blue, slate, gray, zinc, stone, neutral. The client maps the key to the actual (light/dark) colour; null or an unknown key renders in the neutral default colour. Null if unset.

Status codes

  • 200Success
  • 400

    Invalid request (validation error).

  • 401

    Missing or invalid bearer token.

  • 403

    Forbidden (insufficient permissions).

  • 404

    Resource not found or not accessible.

  • 429

    Rate limit exceeded (per token/IP). Transcription uploads may also return code FUP_LIMIT_EXCEEDED or TOO_MANY_CONCURRENT_TRANSCRIPTIONS.

  • 500

    Internal server error.