Authentication
Every request needs an X-Api-Key header:
curl -H "X-Api-Key: $KAMEE_API_KEY" "https://kamee.fit/api/plans"
There is no OAuth, no bearer token, and no signing. The key is compared in constant time, so a wrong key takes the same time to reject as a nearly-right one.
Keep the key server-side
Treat the key like a password:
- Store it in an environment variable or a secrets manager, never in source control.
- Call the API from your backend. Never put the key in browser JavaScript, a mobile app binary, or anything else a user can read.
- Do not put it in a URL — it belongs in the header, where it stays out of logs and
Refererheaders.
By default the API sends no CORS headers, so a browser fetch will fail anyway. That is
deliberate. Calling from a browser covers the
proxy pattern.
What you should know about the current key model
Being straight with you: keys are not currently per-partner. There is one key shared by every integrator. That has two consequences worth planning around:
- There is no self-serve issuance or revocation. Getting or replacing a key means
contacting
PLACEHOLDER_CONTACT. - Rotation is global. When the key rotates, it rotates for everyone at once. Read your key from configuration you can change without a redeploy, so a rotation is a config change rather than a release.
Per-partner keys are on the roadmap. Until then, build for a key that can change out from
under you: read it at request time rather than caching it at process start, and make a
401 a loud, alerting failure rather than a silent empty list.
When authentication fails
A missing, malformed, or wrong key returns 401:
{"error": "Unauthorized."}
401 always means the key. It is never a rate limit and never a signal to back off and
retry — retrying with the same key will fail identically. Treat it as a configuration
error and alert on it.
Full list of responses: Errors.