StackResolve logoStackResolve

Errors

Error format, HTTP status codes, and the entitlement reason codes.

Errors return a JSON body with an error message and an appropriate HTTP status.

JSON
{ "error": "a valid API key is required for this endpoint" }

#Status codes

StatusMeaningTypical bodyFix
400Malformed request{ "error": "missing stripe-signature" }Check the body, query params, and headers
401Missing or invalid API key{ "error": "a valid API key is required for this endpoint" }Send a valid x-api-key (Authentication)
402Plan limit reached (metered call){ "error": "USAGE_LIMIT_REACHED", "entitlement": { ... } }Enable metered billing or raise limits (Billing)
404Unknown route or entity{ "error": "not found" } or { "error": "unknown product" }Check the path or slug
429Anonymous trial limit reached{ "error": "anonymous trial limit reached (8/hour). Get a free API key for more." }Get a free key (Rate Limits)
500Internal error{ "error": "..." }Retry with backoff; report if it persists
503Billing not configured{ "error": "..." }Only on checkout or portal when Stripe is not set up

#Entitlement reason codes

A 402 on a metered primitive carries an entitlement object with a reason. The reason tells you why the call was blocked.

ReasonMeaning
OKAllowed. Not an error.
USAGE_LIMIT_REACHEDThe plan's included quantity for this event type is used up and overage is off
HARD_LIMIT_REACHEDA hard usage cap on this event type was reached
SPEND_LIMIT_REACHEDYour monthly spend hard limit was reached (Limits)

The entitlement object also reports included, used, remaining, and meteredEnabled, so an agent can decide whether to enable billing or wait for the next period.

#MCP errors

The hosted MCP speaks JSON-RPC. A missing or invalid key returns:

JSON
{ "jsonrpc": "2.0", "error": { "code": -32001, "message": "a valid StackResolve API key is required (x-api-key header)" }, "id": null }

A blocked metered tool call returns a tool error whose message names the reason and your used-versus-included counts.

#Resilience

The research primitives are built to degrade, not fail. If a scrape or a single source fails, the call still returns the facts it could gather rather than erroring out, and the freshness block shows what it could and could not refresh.