> ## Documentation Index
> Fetch the complete documentation index at: https://docs.telepatia.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Appointments

> Schedule consultations and track them by their stable public id

Appointments are scheduled consultations. Create a booking, and when the consultation runs it links to the appointment automatically, so the booking moves from `booked` to `fulfilled` on its own.

Every booking carries two ids: the `apt_...` public id we return, and the `consultationInternalId` you choose — your own id for the consultation, and the key that links the booking to the visit.

<Note>
  Appointments are **tenant-scoped by your API key's institution**. A `doctor` or `institutional` key can schedule and update; scoping is enforced server-side, so you never pass an account or institution id. Writes need `scribe:write`, reads need `scribe:read`.
</Note>

## Scheduling an appointment

`POST /v1/appointments` requires `consultationInternalId` and a patient. Reference an existing patient by `patientId` (`sp_...`) or `internalCode`, or send the inline identity (`name`, `idCountry`, `idType`, `idValue`) to create one. Optional scheduling fields: `start`, `end`, `minutesDuration`, `serviceType`, `appointmentType`, `reason`, `description`.

Re-posting the same `consultationInternalId` updates the booking in place (idempotent), as long as you re-post with the key that owns the booking or the key that created it. A new appointment starts as `booked`.

### Whose agenda the booking joins

An appointment belongs to one account, and only that account sees it. By default the booking joins the agenda of the key that created it, so a doctor key needs nothing extra.

An institutional key adds `doctorId` to book for one of its doctors: an account public id (`acc_...`) or your own `internalCode` for that account. The doctor then sees the booking, and so does the institutional key that created it. A doctor key cannot book into another doctor's agenda.

The agenda is fixed when the booking is created. Re-posting the same `consultationInternalId` with a different `doctorId` updates the times and the clinical detail, and leaves the booking where it is. To move a booking to another doctor, cancel it and create a new one.

A key that neither owns the booking nor created it cannot re-post it, and gets 403. If your institution books with more than one key, re-post each booking with the key that created it.

```bash theme={null}
curl -X POST https://scribe-api.telepatia.ai/v1/appointments \
  -H "Authorization: Bearer YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "consultationInternalId": "CONSULT-12345",
    "patientId": "sp_a1b2c3d4e5f6g7h8",
    "start": "2026-09-01T14:00:00.000Z",
    "serviceType": "cardiology"
  }'
```

**Response:**

```json theme={null}
{
  "id": "apt_a1b2c3d4e5f6g7h8",
  "consultationInternalId": "CONSULT-12345",
  "status": "booked",
  "start": "2026-09-01T14:00:00.000Z",
  "end": null,
  "minutesDuration": null,
  "serviceType": "cardiology",
  "appointmentType": null,
  "reason": null,
  "description": null,
  "createdAt": "2026-08-29T12:00:00.000Z"
}
```

<Tip>
  Optionally attach a template — `medicalRecordConfigurationId` (`mrc_...`). When present, the doctor's consultation context is seeded ahead of time, so it is ready before the visit. Set `scribeSessionModality` (`IN_PERSON`, `TELEMEDICINE`, or `DICTATION`) to record how the consultation happens; it takes effect only when a template is attached.
</Tip>

## Listing appointments

`GET /v1/appointments` returns the agenda visible to your key, sorted by start time. Filter by a start-time range (`startFrom`, `startTo`), one or more `status` values (repeatable), or a `consultationInternalId`. Paginate with `page` (1-based) and `limit` (1–50, default 20).

```bash theme={null}
curl "https://scribe-api.telepatia.ai/v1/appointments?startFrom=2026-09-01T00:00:00.000Z&status=booked&limit=20" \
  -H "Authorization: Bearer YOUR_API_KEY"
```

**Response:**

```json theme={null}
{
  "items": [
    {
      "id": "apt_a1b2c3d4e5f6g7h8",
      "consultationInternalId": "CONSULT-12345",
      "status": "booked",
      "start": "2026-09-01T14:00:00.000Z",
      "end": null,
      "minutesDuration": null,
      "serviceType": "cardiology",
      "appointmentType": null,
      "reason": null,
      "description": null,
      "createdAt": "2026-08-29T12:00:00.000Z"
    }
  ],
  "total": 42,
  "page": 1,
  "limit": 20,
  "totalPages": 3,
  "hasMore": true
}
```

<Note>
  `total` and `totalPages` are only computed on the **first page** — they are `null` on later pages to avoid a full scan on every page click. Use `hasMore` to paginate reliably; it is accurate on every page.
</Note>

## Retrieving an appointment

`GET /v1/appointments/{appointment_id}` looks up a single appointment. The `{appointment_id}` can be the public id (`apt_...`) or the `consultationInternalId` you sent at create. Returns `404` if no appointment with that id is visible to your key.

```bash theme={null}
curl https://scribe-api.telepatia.ai/v1/appointments/apt_a1b2c3d4e5f6g7h8 \
  -H "Authorization: Bearer YOUR_API_KEY"
```

**Response:**

```json theme={null}
{
  "id": "apt_a1b2c3d4e5f6g7h8",
  "consultationInternalId": "CONSULT-12345",
  "status": "booked",
  "start": "2026-09-01T14:00:00.000Z",
  "end": null,
  "minutesDuration": null,
  "serviceType": "cardiology",
  "appointmentType": null,
  "reason": null,
  "description": null,
  "createdAt": "2026-08-29T12:00:00.000Z"
}
```

## Updating an appointment

`PATCH /v1/appointments/{appointment_id}` cancels a booking or marks it a no-show, by its public id (`apt_...`) or `consultationInternalId`. Set `status` to `cancelled` or `noshow` — `fulfilled` is set only by the server when the consultation runs. Send exactly one of `status` or `scribeSessionId`. Returns `404` if no appointment with that id is visible to your key.

```bash theme={null}
curl -X PATCH https://scribe-api.telepatia.ai/v1/appointments/apt_a1b2c3d4e5f6g7h8 \
  -H "Authorization: Bearer YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "status": "cancelled"
  }'
```

**Response:**

```json theme={null}
{
  "id": "apt_a1b2c3d4e5f6g7h8",
  "consultationInternalId": "CONSULT-12345",
  "status": "cancelled",
  "start": "2026-09-01T14:00:00.000Z",
  "end": null,
  "minutesDuration": null,
  "serviceType": "cardiology",
  "appointmentType": null,
  "reason": null,
  "description": null,
  "createdAt": "2026-08-29T12:00:00.000Z"
}
```

<Note>
  To repair a booking whose session was not auto-linked at create time, send `scribeSessionId` (the session's `ss_...` id) instead of `status`. It attaches the session and marks the booking `fulfilled`. This only applies to a booked, unlinked booking; anything else returns `409`.
</Note>
