Skip to main content
An appointment is a scheduled blood draw session for a patient profile at a physical test location, performed by a healthcare professional. Kits mailed to a patient are not appointments — see Home Kit Orders.

Fields

string
required
UUID auto-generated by Aniva. Use this to add panels, confirm the draw, and retrieve results.
string
required
The UUID of the profile this appointment belongs to.
string
The UUID of the test location where the draw will take place. Null for home kit appointments.
string
Scheduled blood draw datetime in ISO 8601 format. Always returned as a UTC instant with a Z suffix (e.g. 2026-04-15T08:30:00Z). On create / update the value must include a timezone designator (either Z or an explicit offset like +02:00) — naive datetimes are rejected. Must be in the future, and at Aniva-operated locations at least 12 hours out (minimum notice).
string
required
Current lifecycle status. One of pending, confirmed, blood_drawn, or cancelled. See Lifecycle below. Lab-result completion granularity (in_progress vs completed) is derived from Get Results; finer-grained shipment progression (in transit, delivered, etc.) is derived by following each entry in the inline shipments array to Get Shipment.
string
Free-text reason captured when the appointment was cancelled (e.g. no-show, late cancellation, ‘Failed. Repeat required’). null unless status is cancelled.
string
required
ISO 8601 timestamp of when the appointment was created.
string
ISO 8601 timestamp of the most recent update. Null if the appointment has never been updated.
object
The full profile object for the patient, embedded in every appointment response.

Lifecycle

Appointments expose four lifecycle states:
The appointment status surface is intentionally coarse — finer-grained progression is exposed via dedicated endpoints:
  • Lab result completionGet Results — top-level status field is in_progress or completed.
  • Shipment progression (in transit, delivered, etc.) → follow each entry in the inline shipments array on the appointment to Get Shipment — each shipment carries its own status and a status_updates event log.
Confirming an appointment (moving it to blood_drawn) is irreversible. Once you submit the kit barcode, the lab order pipeline is triggered and cannot be undone. Updates and cancellations are only allowed while the appointment is in pending or confirmed status.

Listing appointments

Retrieve all appointments accessible to your API key:
Optionally pass ?profile_id={uuid} to filter by a specific profile. Without this parameter, a default time window (past 2 months to future 1 month) is applied.

Updating an appointment

Before the blood draw is confirmed, you can reschedule or change the test location:
Pass any combination of scheduled_at and location_id to update. Only include the fields you want to change.

One appointment per profile, location and time

A profile holds at most one non-cancelled appointment per (location_id, scheduled_at) pair — one person cannot be drawn twice at one place at one moment, independent of how many parallel bookings the location accepts. Both Create Appointment and Update Appointment enforce this, returning 409 with an appointment_id pointing at the appointment that already exists. Treat that response as “already booked” rather than an error to retry: fetch, reschedule, or cancel the appointment it names. The practical effect is that repeated creates are safe. A create you resend after a network timeout, or one a user triggers twice, resolves to a single appointment instead of two — which also means you never need to reconcile duplicate bookings for the same patient after the fact.
Updates are only allowed before the blood draw — i.e. while the appointment is in pending or confirmed status. Once the appointment moves to blood_drawn or has been cancelled, it cannot be modified.

Cancelling an appointment

Cancel an appointment that is no longer needed:
This sets the appointment status to cancelled. The cancelled appointment is returned in the response. Optionally send a cancellation_reason (up to 500 characters) in the body to record why. It is stored on the appointment and returned as cancellation_reason on later reads.
Cancellation is only allowed before the blood draw — i.e. while the appointment is in pending or confirmed status. Appointments that have already moved to blood_drawn cannot be cancelled.

Adding panels

Before confirming the blood draw, add the blood test panels you want to run by calling:
Pass an array of panel UUIDs in the panel_ids field. Panel IDs are provided by Aniva for your partner account.
Panels must be added before the blood draw — i.e. while the appointment is in pending or confirmed status. You cannot add or change panels once the appointment has moved to blood_drawn.

Removing panels

If you need to remove panels before the blood draw, call:
Pass an array of panel UUIDs in the panel_ids field. All specified panels must currently be associated with the appointment.
Like adding panels, removal is only allowed before the blood draw — i.e. while the appointment is in pending or confirmed status. Panels cannot be removed once the appointment has moved to blood_drawn.

Individual biomarkers

You can attach individual biomarkers to an appointment as à la carte tests, outside any pre-built panel. This is useful when a practitioner wants a tailored selection rather than a pre-defined bundle. The attached biomarkers surface on the appointment response as a individual_biomarkers array (siblings of panels). Routing decisions are made downstream by the order-logistics pipeline based on each biomarker’s per-lab mappings. Add biomarkers (idempotent — already-attached biomarkers are kept):
Remove biomarkers (every ID must currently be attached, otherwise 404):
Both endpoints take a biomarker_ids array and validate the resulting set against each lab’s closure rules — an order that can’t be cleanly placed (e.g. a CRP/HDL ratio without CRP and HDL) returns 400 with the biomarkers you’d need to add, and persists nothing. Use List Biomarkers to discover biomarker IDs.
À-la-carte biomarkers are not pre-validated on add/remove — incoherent combinations are accepted at write time and may surface as ordering failures later in the lab pipeline.
Like panel modifications, individual biomarkers can only be added or removed before the blood draw — i.e. while the appointment is in pending or confirmed status. Once the appointment moves to blood_drawn the custom snapshot is frozen.

Previewing container requirements

After adding panels or individual biomarkers, preview the physical specimen-collection containers that will be needed for the sample collection:
The response’s containers array includes the type, name, kind (monovette/dbs_card/urine_cup), cap color, volume, Sarstedt article number, and count for each required container. This helps practitioners prepare the correct materials before the blood draw. The response also carries a pricing object — the appointment’s whole-cart pricing (billing groups plus a total, at both the retail card and your own card), populated when the appointment has a location and attached tests and your key has the prices_view scope, otherwise null. routing is intentionally never exposed and is always null.
The preview reflects the currently attached panels and biomarkers. If you add or remove panels after previewing, call the preview endpoint again to get updated container requirements.

Confirming the blood draw

After the blood is drawn, submit the kit barcode to trigger the lab order pipeline:
This moves the appointment status to blood_drawn and initiates lab processing. This action is irreversible.

Shipment pickup

POST /api/v1/appointments/pickup has been removed, along with the shipment_picked_up appointment status. It now answers 405 Method Not Allowed, because the path falls through to the appointment-by-id route. The endpoint spent its final phase as a no-op that accepted the call and did nothing, so removing it changes no behaviour you were relying on.
To track post-blood-draw progression, follow each entry in the appointment’s inline shipments array to Get Shipment — each shipment carries its own status and a status_updates history.

Linking shipments

An appointment can be linked to one or more shipments (and vice versa — the relation is many-to-many). The current link set surfaces inline on both sides:
  • on the appointment, as a shipments array of { id, added_at } entries;
  • on the shipment, as an appointments array of { id, added_at } entries.
Both arrays are oldest-link first. Each id cross-references the canonical detail endpoint (Get Shipment / Get Appointment) for the full payload. Shipments are linked at creation time via the appointment_id field on Create Shipment. After creation, manage links from the shipment with Attach Appointments to Shipment and Detach Appointments from Shipment; each returns the post-mutation appointment list for that shipment. To read an appointment’s parcels in full, use List Shipments with ?appointment_id=. The mutation rule is: links can be created or removed when EITHER
  • the appointment is past blood-draw (blood_drawn), or
  • the shipment was created less than 24 hours ago.
Outside that window the link is locked so historical records stay stable.

Retrieving lab results

Once the lab has processed the blood samples, retrieve clinical and genetic results:
The response includes planned tests (status planned) alongside received results, so you can track what is still pending. The top-level status field is in_progress until every submission arrives, then completed — use this to derive whether the appointment’s lab work is done. Lab report PDFs are referenced in the documents array — use GET /api/v1/documents/{id} to download them.

Example appointment