The Relata API
Everything the interface does, /api/v1 does too. Authenticate with a bearer
token you create for yourself.
Getting a token
Sign in, then go to Settings → API tokens. Choose a name, the scopes it needs, and how long it should live.
The token is shown once. Relata stores only a SHA-256 hash of it, so a database read — or a backup — yields nothing that can authenticate. If you lose it, revoke it and make another.
Scopes
| Scope | Permits |
|---|---|
query | Search, generate answers, and read stored items, entities and relationships. |
ingest | Create items, upload files, reprocess and delete. |
review | Confirm, reject and retype relationships; confirm entity aliases. |
A token never carries more than the role of the person who created it. The check is the intersection of the two, so demoting someone immediately narrows every token they hold without any of those tokens being touched.
Using it
export RELATA_TOKEN='rlt_v1_...'
# Search
curl -s -H "Authorization: Bearer $RELATA_TOKEN" \
'https://relata.example/api/v1/search?q=delivery+schedule&limit=5'
# Ingest a note
curl -s -X POST -H "Authorization: Bearer $RELATA_TOKEN" \
-H 'Content-Type: application/json' \
https://relata.example/api/v1/items \
-d '{"title":"Meeting note","content":"The revised cost is 51,500.","source_type":"note"}'
# Ask a question of what is stored
curl -s -X POST -H "Authorization: Bearer $RELATA_TOKEN" \
-H 'Content-Type: application/json' \
https://relata.example/api/v1/search/answer \
-d '{"question":"What is the project cost?"}'
Bearer requests do not need a CSRF token: CSRF exists to stop a third-party page spending
ambient credentials, and an Authorization header is not ambient — a
browser never attaches one on its own.
What a token cannot do
- Reach the web interface. Tokens authenticate
/api/v1only. - Manage tokens. Creating, listing and revoking tokens requires a signed-in session, so a leaked token cannot mint its own replacements or extend its life.
- Outlive its expiry or revocation. Both are checked on every request against the stored record. There is no cached grant to wait out.
- Exceed your role. Scopes narrow permission; they never widen it.
Errors
Every error is a stable code with a safe message and a request ID:
{
"error": {
"code": "insufficient_scope",
"message": "This API token does not carry the scope this request needs.",
"detail": { "required_scope": "ingest" },
"request_id": "b3f1c0d2-…"
}
}
Rate limiting is per token. A token making too many requests gets 429 with
rate_limited; the limit resets on a fixed window.
For operators
The redirect URI to register with your identity provider is:
https://relata.dixon.cx/auth/oauth/callback
The path is fixed at /auth/oauth/callback; only the host varies. The full
OpenAPI specification is in the repository at docs/openapi.yaml.