Error catalog

Every error, one shape.

All errors are JSON with the same three fields. Log the whole body: the message is written for humans and usually names the exact parameter or id that caused it.

{ "error": "bad_request", "message": "Missing required parameter: from", "status": 400 }
400 Bad Request your input

A parameter is missing, malformed, or unusable: a missing required from date, a non-numeric id in product_ids, an unknown flag value. The API refuses rather than guessing; a typo in product_ids is a 400, never a silently-full catalog.

React: fix the request. Do not retry unchanged; the same input gives the same 400.

401 Unauthorized auth

No bearer token, an expired one (tokens live 30 minutes), or one this account cannot use.

React: re-authenticate (POST /api/auth/login or /api/auth/refresh) and retry once. Better: refresh proactively around the 25-minute mark. See Integration patterns.

404 Not Found your input

The id does not exist on this account (an order, customer, product, or location), or the path itself does not exist. Ids are per-account: an order id from one account never resolves on another.

React: treat it as data, not as an outage. If you stored the id earlier, the record was removed or you are calling with the wrong account's token.

429 Too Many Requests rate

Reserved. Rate limiting is being introduced together with API keys; when it activates, responses will carry standard rate-limit headers and this page will document them.

React: build your client to back off on 429 today and you will never notice the change.

500 Internal Server Error ours

A fault in the API layer itself. The response never echoes internals.

React: retry with backoff. If it persists, report it with the timestamp and the path; we log every request and can trace it.

502 Bad Gateway upstream

The Storekeeper platform behind the API rejected or failed the call. The message carries the upstream reason when it is safe to share.

React: safe to retry with backoff for reads. If the message names a business reason (an id in use, a missing configuration), fix that instead of retrying.

Timeouts and connection errors without a JSON body mean the request may or may not have been processed. For the read API that is always safe to retry.