> For the complete documentation index, see [llms.txt](https://docs.tryterra.co/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.tryterra.co/vantage-api-docs/core-concepts.md).

# Core concepts

## The catalog: product types → products → variants

The catalog is three levels deep:

| Level            | What it is                                                             | Example                                                           |
| ---------------- | ---------------------------------------------------------------------- | ----------------------------------------------------------------- |
| **Product type** | The broadest category                                                  | Blood Test, DNA Test                                              |
| **Product**      | An offering within a type                                              | An at-home blood test kit from a given supplier                   |
| **Variant**      | The exact configuration an end user receives - **the thing you order** | The "Inflammation" panel (hs-CRP + Vitamin D), 3-5 day turnaround |

You browse with `GET /api/v1/products` (types) → `GET /api/v1/products/{product_type_id}` (products) → `GET /api/v1/products/{product_id}/variants` (variants), and you order a `variant_id`. A variant advertises which collection methods it supports in `available_collection_types` (an array of strings: `"AT_HOME"`, `"GO_TO_LAB"`).

Your catalog is scoped to your contract: browsing returns only the panels and fulfilment options your account is entitled to, and orders for anything outside it are rejected. To add panels to your contract, contact the Terra team. Within your entitlements, you can additionally curate which products your catalog reads return - see [Managing orders](/vantage-api-docs/documentation/managing-orders.md#curating-your-catalog).

## Orders and order items

An **order** is one purchase: it has a recipient, a collection type, an address, and one or more **order items** (one per `variant_id` + quantity). Everything result-related happens **per order item**: kit activation, result statuses, result downloads, and acknowledgment are all keyed by `order_item_id`, not `order_id`.

* `client_order_reference_id` - **your** unique identifier for the order, supplied when you create it. Use it to reconcile webhooks and REST reads with your own system. For retry-safe creation, send an `Idempotency-Key` header - the reference id alone does not deduplicate.
* `order_id`, `order_item_id`, `recipient_id`, `test_taker_id` - Terra-generated identifiers.

{% hint style="warning" %}
**Treat IDs as strings.** All Vantage identifiers are 64-bit values serialized as JSON strings (e.g. `"251285377984405504"`). Parsing them as floating-point numbers (the default in JavaScript) silently corrupts them. Store and compare them as strings.
{% endhint %}

## Recipient vs test taker

* The **recipient** is the person the order is placed for - name, date of birth, gender at birth, email, phone. You provide it at order time.
* The **test taker** is the person who actually takes the test. For suppliers with kit activation, the test taker registers themselves during activation (and may differ from the recipient, supplier-permitting). Terra assigns a `test_taker_id` at that point and includes it in every result webhook.

You need the `test_taker_id` to fetch and acknowledge results - capture it from the result webhooks (or from `GET /api/v1/orders/{orderID}`).

## Collection types

Every order has a `collection_type` that determines how the sample is collected and which address field the order requires:

| `collection_type` | Meaning                                                  | Address field           |
| ----------------- | -------------------------------------------------------- | ----------------------- |
| `AT_HOME`         | Kit shipped to the recipient, who self-collects          | `shipping_address`      |
| `GO_TO_LAB`       | Sample drawn at a lab draw site (Patient Service Center) | `requested_lab_address` |

See [Test Collection Methods](/vantage-api-docs/documentation/test-collection-methods.md).

## Status lifecycles

An order carries a fulfilment status; each order item carries a results status.

**Order (fulfilment) statuses**, as returned by the REST API:

```
order.payment_processing → order.payment_complete | order.payment_failed | order.cancelled
order.payment_complete   → order.processing | order.cancelled
order.processing         → order.delayed | order.delivery_fulfilled | order.cancelled
order.delayed            → order.delivery_fulfilled | order.cancelled
order.delivery_fulfilled → order.completed
```

New orders start at `order.payment_processing`.

**Order item (results) statuses:**

```
results.awaiting_sample          → results.kit_activated | results.sample_rejected
results.kit_activated            → results.sample_processing_in_lab | results.sample_rejected
results.sample_processing_in_lab → results.partial_results_ready | results.results_ready
                                   | results.lab_processing_error | results.escalation_raised
                                   | results.sample_rejected
results.partial_results_ready    → results.results_ready | results.escalation_raised
results.results_ready            → results.escalation_raised
```

{% hint style="warning" %}
REST endpoints and webhook payloads use the same `order.*` vocabulary for fulfilment statuses (and the same `results.*` vocabulary for results statuses) - a status seen on a webhook can be matched verbatim against any REST read of the order.
{% endhint %}

## Escalation levels

Results carrying clinical escalation include an `escalation_level`, one of (in ascending severity):

`not_escalated`, `very_low`, `low`, `medium`, `high`, `very_high`

Escalated results also carry an `acknowledgment_due_by` timestamp - see [Acknowledging Results](/vantage-api-docs/important-information/acknowledging-results.md).

## Conventions

* **Money** is integer cents (`price_cents`, `total_cents`); **currency** is an ISO 4217 numeric code (`840` = USD, `978` = EUR, `826` = GBP).
* **Phone numbers are a single E.164 string everywhere** — the industry-standard format used by Stripe, Twilio and FHIR. Send `phone_number` as a `+`-prefixed E.164 string (`"+14155551234"`); reads and webhook `test_taker` payloads return the same string. There is no separate recipient `country_code` field.
* **Timestamps** in webhook payloads (`timestamp`) are Unix seconds; REST timestamps are RFC 3339 strings.
* **Errors** follow RFC 7807 problem-detail format - see [Errors](/vantage-api-docs/documentation/errors.md).
* **List endpoints** (`GET /api/v1/orders`, `GET /api/v1/results`, `GET /api/v1/webhook-deliveries`) are keyset-paginated: pass the returned `next_cursor` as `?cursor=` for the next page; a page without `next_cursor` is the last one.
