Skip to main content
The Console is built on the same REST API you can call directly. Base URL:
An OpenAPI schema and interactive explorers are served by the API itself at /api/schema/, /api/docs/ (Swagger UI), and /api/redoc/. Coding agents get the same surface as typed tools over MCP.

Authentication

Three ways to authenticate; the first is right for almost all programmatic use: A key has a scope: project pins it to one project, account reaches every project the user is a member of. MCP requires a project-scoped key. Keys are created and revoked under Projects → your project → API keys or via the API:
Keys do not expire; revoke what you no longer need.

Endpoint map

Standard REST resources follow Django REST Framework conventions: GET list with query-param filtering, POST create, GET/PATCH/DELETE on /{id}/, plus the custom actions listed here.

Core resources

Evaluation

Optimisation, training, serving

Special endpoints

Building a dataset

A dataset lands its rows as-is and its agent shapes them cell by cell; a run uses one version. The same sequence backs the Console, the CLI, and the MCP dataset tools.
1

Land a source

A file goes up in chunks (POST /api/uploads/, then PUT /api/uploads/{id}/chunk/?offset=). POST /api/datasets/ with project, name, optional intent (train or eval) and capability, and exactly one source: upload_id (+ filename), rows or text for pasted data, or traces (trace_ids, or a trace-list selection of filters and/or search; one row lands per trace, and an interrupted trace with no root span lands like any other). The selection is validated and counted first: an unknown filter key or a selection that matches no trace is a 400, so a dataset never lands empty. POST /api/datasets/split/ takes the same body plus eval_percent and position and returns {train, eval}. The response is the dataset; landing runs in the background, state moves from landing to diagnosing while the agent runs its preparation turn, then idle. Landing proposes capability_rank and the intent when they were left out.
2

Shape it

POST /api/datasets/{id}/cells/ adds a cell (title, script, note) at the end of the chain; PATCH .../cells/{id}/ edits it and queues every cell after it; POST .../run/ executes the queued cells in order (an unchanged cell keeps its frame). POST .../chat/ sends a message to the dataset’s agent, which lands cells itself. GET .../events/ streams cell_started, cell_done, cell_failed, run_done, run_failed, chat_turn, chat_step, chat_delta and chat_cell as server-sent events.
3

Read a version

The dataset’s cells carry every version: version, state, rows, columns, intent_report and capability_report, fits against the intent, stats, and frozen. GET .../rows/?cell=&diff=1 pages a frame with marks (rows added, values changed with the old value).
4

Use it

Eval runs, optimiser experiments and finetuning jobs take dataset and, optionally, cell; without it the active version is used. A version whose contracts do not fit the intent, a dataset of the other intent, or a cell of another dataset, is refused with the reason. A use freezes the version and starts a new major number.
5

Pull it

A local loop reads the used version, never the dataset: GET .../export/?fmt=jsonl&cell={id}. The response carries X-Overmind-Cell, X-Overmind-Version and X-Overmind-Fingerprint; the SDK caches the file as .overmind/datasets/{cell}.jsonl with the fingerprint beside it and fetches again when it no longer matches.

Conventions

  • Filtering uses django-filter query parameters on list endpoints (the Console’s filter bar builds exactly these URLs — copy them from your browser).
  • Errors: 401 unauthenticated, 402 insufficient credits for compute-consuming actions when the credit gate is on (hosted; trace ingest is never credit-gated), 403 plan limits, 404 wrong project or missing resource.
  • IDs are UUIDs except spans (16-hex span_id) and traces (32-hex trace_id).