Signup comes with $1 in credit. No subscription needed.Claim your $1
Docs: Errors
API reference

Errors

Stable error codes, HTTP statuses, the error envelope and retry guidance.

Every error, from any endpoint, uses one envelope with a stable, enumerable code:

{
  "error": {
    "code": "insufficient_balance",
    "message": "Top up your wallet to run this call.",
    "request_id": "req_1f2e...",
    "details": {"optional": "structured context"}
  }
}

Branch on code, show message to humans. An error the message does not explain is worth a feedback report with its request_id (free); every error response carries Link: </feedback>; rel="agent-feedback" to point agents there. People can write to hello@routergrowth.com.

Codes

Code HTTP Meaning Retry?
invalid_request 400 malformed body, unknown field or bad value fix the request
invalid_api_key 401 missing, malformed or revoked key no
invalid_credentials 401 bad dashboard sign-in no
forbidden 403 the key cannot do this (for example: sandbox-only routes on production) no
capability_not_found 404 unknown capability slug no; discover first
endpoint_not_found 404 unknown raw endpoint for that provider no; list /v1/catalog/providers/{provider}/endpoints
no_match 404 providers answered authoritatively: no result not with the same input
insufficient_balance 402 reservation exceeds available balance after a top-up
cost_limit_exceeded 402 the run's hold exceeds the workspace's per-run ceiling; the run is blocked lower the call or raise the ceiling at /v1/spend-guard
budget_exceeded 402 the daily spend guard would be breached; the run is blocked after the UTC reset, or raise the cap
suppressed 403 a recipient of the send is on the workspace's suppression list; the run is blocked, nothing charged do not send; remove the suppression only if the person asked to hear from you again
opted_out 403 the recipient of the send opted out with RouterGrowth itself (privacy policy); binds every workspace; the run is blocked, nothing charged no
repeat_touch 409 a new conversation with someone contacted on the same channel inside the repeat window; the run is blocked, nothing charged reply in the existing thread, or pass routing.allow_repeat with the user's say-so
paced 429 a send from a connected account inside its minimum gap or over its day's ceiling (send pacing); the run is blocked, nothing charged after details.retry_after seconds
duplicate_request 409 conflicting concurrent request no
not_found 404 no such route no
payload_too_large 413 request body above 1 MB with a smaller body
provider_not_available 409 no live provider for this capability yet, or a provider not exposed raw later
rate_limited 429 too many requests from your client (counted per key, with a wider cap shared by every key on one IP; per IP for calls without a key, and tighter on sign-in, code requests and OAuth registration); Retry-After says when after Retry-After
provider_rate_limited 429 the upstream provider throttled us with backoff
provider_error 502 the upstream provider failed; nothing charged yes, with an Idempotency-Key
provider_timeout 504 the upstream provider timed out; nothing charged yes, with an Idempotency-Key
internal_error 500 our fault; nothing charged without settlement yes, with an Idempotency-Key
interrupted none (on the run) the router restarted while the run was executing; the run is failed and its hold released yes, with a new Idempotency-Key

Retrying safely

Retry provider_error, provider_timeout, internal_error and both rate limits with exponential backoff. When the answer was lost (a timeout, a dropped connection), resend the same Idempotency-Key: a retry that races a completed run gets the original result back (Idempotent-Replay: true) instead of a second charge. When you did get a failed run back, retry with a new key: the old one returns that same failed run.

On auto routing, most provider failures never reach you: a rate-limited or 5xx provider is retried once after a short wait, and the waterfall tried the next-best provider before returning an error. When max_cost kept a fallback from running, the error message names it and the cap that admits it: raise the cap once rather than resubmitting the same call.

Send pacing

Sends from a connected account (linkedin.invite, linkedin.message, instagram.message) keep a minimum gap and a daily ceiling on the platform side, whatever the agent asks for. A day here is the UTC calendar day: the count starts again at 00:00 UTC, and the whole allowance comes back at once. A send inside the gap, or past the ceiling, ends as a blocked run with error paced: nothing is reserved, nothing reaches the network. details.retry_after says how many seconds to wait (with jitter, so the next send does not land on a fixed interval either), and details.sent_today / daily_cap (with resets_at, the next 00:00 UTC) or sent_this_week / weekly_cap say which ceiling held. The week is the last 7 days, rolling. Runs still in flight count as sent, so a parallel burst is refused from its second call.

Capability Gap Per day, reset at 00:00 UTC (account connected under 7 days / under 30 / older) Per 7 days
linkedin.invite 60 s 20 / 30 / 30 180
linkedin.message 15 s 40 / 80 / 150 none
instagram.message 30 s 20 / 50 / 100 none

These sit under LinkedIn's and Instagram's own limits, which are unpublished and tighten on a freshly connected or bursting account. Sandbox keys are not paced. The ceilings count sends made through RouterGrowth; what the account sends elsewhere still counts for the network.

Reading this as an agent? This page as markdown: /docs/api/errors.md · every page: /docs/llms.txt