Every Minima API request is authenticated with an API key sent in the x-api-key header. There are no other authentication methods, and there is no OAuth flow.
curl https://api.minima.ltd/api/v1/me \
-H "x-api-key: priv_your_key_here"That endpoint is the fastest way to check a key works. It needs nothing but the key itself, and it answers with what the key can do:
{
"key": { "id": "key_...", "name": "Production", "type": "admin" },
"role": "admin",
"organizationId": "org_...",
"siteId": null,
"siteScope": null,
"permissions": ["entities:read", "entities:write", "..."]
}Use it when you are setting up. It is also the only route that resolves entirely from the key — every other organization route needs your organization ID in the path, so /me is how you discover which organization a key belongs to.
Two APIs, one host
Everything lives under https://api.minima.ltd/api/v1. Below that base URL there are two separate APIs, and which one you want depends on whether you are building a front end or an integration.
| Admin API | Public API | |
|---|---|---|
| Path | /{orgId}/… |
/public/sites/{siteId}/… |
| Key prefix | priv_ |
pub_ |
| Scope | Your whole organization | One site |
| Methods | Read and write | Read only |
| Content | Drafts and published | Published only |
| Safe in a browser | No | Yes |
The Public API is the one you build a website against. Its routes live under /public/sites/{siteId}/, it returns only published content, and it is CORS-enabled for GET so you can call it from the browser.
The Admin API is everything else — creating and updating content, managing sites, publishing. Its keys can do destructive things, so they belong on a server.
See API keys for how the two key types differ and how to create one.
Your first Public API request
A Public API key is bound to a single site, so every request names that site in the path:
curl https://api.minima.ltd/api/v1/public/sites/site_abc123/articles \
-H "x-api-key: pub_your_key_here"The site in the URL must be the site the key is scoped to. Calling a different site with the same key returns 403, not an empty result.
Because these responses carry no credentials, the Public API sends permissive CORS headers for GET and OPTIONS, and x-api-key is an allowed request header. Fetching directly from the browser works:
const response = await fetch(
"https://api.minima.ltd/api/v1/public/sites/site_abc123/articles",
{ headers: { "x-api-key": "pub_your_key_here" } },
)
const { data } = await response.json()Your first Admin API request
Admin routes are scoped to your organization, which appears in the path:
curl https://api.minima.ltd/api/v1/org_abc123/entities \
-H "x-api-key: priv_your_key_here"Get your organization ID from /me, or from the URL in the Minima dashboard.
When authentication fails
Failures come back as JSON with a matching HTTP status.
{
"url": "/api/v1/me",
"status": 401,
"statusCode": 401,
"statusMessage": "Invalid API key",
"message": "Invalid API key",
"error": true
}| Status | Message | What happened |
|---|---|---|
401 |
Missing API key |
No x-api-key header was sent |
401 |
Invalid API key |
The key is not recognised, or it has been revoked |
403 |
Unauthorized |
The key is valid but does not cover this organization, site, or action |
A revoked key and a key that never existed both return Invalid API key. That is deliberate — telling you which one it was would confirm a guess for anyone probing keys. If a key stops working unexpectedly, check whether it was revoked in Settings rather than reading anything into the message.