> For the complete documentation index, see [llms.txt](https://boundaryai.gitbook.io/boundaryai-docs/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://boundaryai.gitbook.io/boundaryai-docs/api-and-webhooks/changelog.md).

# API changelog

What changed in the API, and what we promise about compatibility.

The API surface is versioned (the current version is in the spec's `info.version` and served at `/api/v1/openapi.json`). This page tracks wire-contract changes and states the compatibility rules your integration can rely on.

***

### Compatibility promise

We follow semantic versioning on the API surface:

* **Major** (breaking) changes move the URL prefix (`/api/v1/` to `/api/v2/`) and are preceded by `Deprecation: true` + `Sunset: <date>` headers on the old endpoints for at least a full release cycle. None have happened.
* **Minor** changes are backward-compatible additions: new endpoints, new optional request fields, new response fields, new webhook events.
* **Patch** changes are clarifications only.

What we will never do without a major version: remove or rename a field or operation, tighten a field's type, change a success status code, or narrow an enum.

**What your client should do:** ignore unknown response fields, tolerate new webhook event types, and treat error `code` values (not messages) as the machine-readable contract.

{% hint style="info" %}
**About the `Deprecation` and `Sunset` headers you see today.** Every 2xx Input API response currently carries them. They announce the **response envelope migration** only: at the sunset date, success payloads switch from the bare shape shown in the examples to the `{"data": ...}` wrapper the schemas declare. No endpoint is being deprecated. Read the payload from `data` when that key is present and from the root otherwise, and your client is correct on both sides of the switch.
{% endhint %}

***

### September 2026: published host, synchronous bulk push

* **The reference now names the host that serves the Input API.** Every Input API operation carries `https://boundaryai-ingest-279197672085.europe-west9.run.app` as its server. The dashboard host (`app.*`) serves the web application and answers API paths with an HTML page and HTTP 200; clients generated against the earlier reference were parsing that page as a success body. Rebuild from the current reference, or point your base URL at the ingestion host. Both vocabularies and every route are unchanged.
* **Synchronous bulk push.** `POST /feedback/push/bulk` (and `/content/push/bulk`) accepts `"sync": true` and returns the completed result with **200** instead of a task id with 202, for batches of up to 50 items across up to 20 fields. Every row must carry an `external_id` (`SYNC_REQUIRES_EXTERNAL_ID`, 400); larger batches and busy moments fall back to the asynchronous 202 path. A batch in which no field accepted anything returns 400 `PUSH_FAILED`; a batch that exceeds its 60-second budget returns 504 `SYNC_PUSH_TIMEOUT`. See [Pushing feedback](/boundaryai-docs/api-and-webhooks/pushing-feedback.md).
* `source_reference` on bulk pushes is now stored on every row (it was validated and then dropped; single pushes were unaffected).
* `GET /me` gained `org_name`, the human-readable label of the organisation the key belongs to.
* **MCP server**: a seventh tool, `get_theme_verbatims`, reads the comments behind one grouped theme; and Claude or ChatGPT users can connect by signing in from the assistant, with per-connection approval, instead of handling a key. See [Connect AI assistants](/boundaryai-docs/api-and-webhooks/mcp.md).

### 1.3.1: analysis read-back for time-tracked groups (September 2026, behaviour fix)

No schema change; `analysis_id` was always nullable. `GET /sources/{id}/analysis` for a source whose feedback group tracks feedback over time used to return `analysis_status: "none"` with all-zero figures even when every period was analysed, because such a source has no single all-time run. It now returns `analysis_status: "available"` with the sentiment distribution and themes aggregated across every analysed period (the same corpus as the dashboard's Overall view) and `analysis_id: null`. Clients that key "is this source analysed" on `analysis_id` should key on `analysis_status`, the documented contract since 1.1.0. The MCP `list_themes` tool likewise now reads the grouping the dashboard shows and accepts a `period_key`.

### 1.3.0: qualitative studies additions (August 2026)

Additive changes to the qualitative studies (interview analysis) API used by the platform's own qualitative workflow: transcript-only runs, and `.txt` / `.docx` transcript uploads alongside recordings. This surface is not part of the published integration reference; the Input API, invites, and webhooks are unchanged in this version.

### 1.2.1: integrator audit corrections (July 2026, patch)

A cold-integrator audit against the public reference. No endpoint shapes changed; every item either corrects the reference to match the wire or fixes behaviour that violated the documented contract.

Behaviour fixes:

* **Rate-limit windows are fixed**, anchored at the first request. Previously every request, including rejected ones, extended the window, so a client polling faster than the window never recovered; `Retry-After` is now exact.
* **Idempotency conflicts (409)** on API-key routes use the Input API error envelope.
* **Validation errors on the recommended routes** speak the recommended vocabulary (`field`, not the classic `question`).
* **`numeric` values in `GET /feedback`** are JSON numbers (they were serialised as strings); non-finite numeric content is rejected at ingestion.

Reference corrections: request and response examples on every operation; every write operation states the key permission it requires; bulk `progress` documented as a percentage (0-100); push responses document `rows_accepted` and the group/source ids, with `aps_deducted` as a legacy alias; `GET /me` credits fully typed; the 9-event webhook catalogue with payload schemas; the envelope-migration note above.

### 1.2.0: Survey invite distribution (July 2026)

Trigger personalized survey-invite emails from the API, using the template designed in the platform.

* `GET /sources/{id}/invite-template`: template presence, variables, sender-domain status, quota usage.
* `POST /sources/{id}/invites`: transactional send, 1 to 1,000 recipients per call, with per-recipient `variables`, `dry_run` previews, and a `resend` override of the never-double-invite default.
* `GET /invites/{id}` and `/invites/{id}/recipients`: distribution status and per-recipient outcomes, including delivery status.
* New **`send` key permission**; API sends require your organisation's own verified sending domain.
* New webhook events: `invites.completed`, `invite.bounced`.

### 1.1.0: Input API improvement pass (July 2026)

* **Recommended vocabulary**: the API now speaks `feedback_group` / `source` / `field` alongside the original `survey_series` / `survey` / `question`. Same handlers, both key sets accepted; the classic routes are unchanged and not deprecated. See [Concepts & naming](/boundaryai-docs/api-and-webhooks/concepts-and-naming.md).
* **Structured content items** on push: `{text, external_id, customer_id, channel, language, rating, occurred_at}`. `external_id` deduplicates retried pushes; `occurred_at` back-dates items into the right tracking period.
* **Analysis read-back** via `GET /sources/{id}/analysis`: sentiment distribution, themes, monitor matches.
* **New webhook events**: `analysis.completed`, `flag.raised`, `report.ready`.
* **Data controls**: `POST /feedback/erase` (bulk erasure by `external_id` or `customer_id`), `GET /feedback` (cursor listing of API-pushed items), `POST /feedback/upload` (CSV/XLSX async ingest), `GET /me` (key introspection).
* `feedback_type` on source creation (`survey`, `call_transcript`, `app_review`, `support_ticket`, `chat`, `email`, `social_media`, `review`, `other`).
* Listings became paginated (`limit` default 50, max 200, with a `pagination` echo); a source takes up to 100 fields per create call.

### 1.0.0: Initial public spec (May 2026)

First published OpenAPI 3.1 description of the integration surface: content push (single + bulk), group/source/field creation and publishing, API-key auth with scoped permissions, idempotency keys, cursor pagination, rate-limit headers, and the first four webhook events (`content.pushed`, `series.created`, `survey.created`, `survey.published`) with signed deliveries.
