Saylor InnovationsSAYLOR INNOVATIONS

Home / Guides / Self-Hosting & Infra

API Error Resolver

Self-Hosting & Infra intermediate 8 min read Free Updated 2026-08-22

Method for turning a failed API call into a corrected, reproducible request: build a minimal repro, classify the failure by layer (transport/auth/validation/authorization/throttling/server), fix the right one, and add a regression test that distinguishes them going forward.

An API failing with a vague 4xx or 5xx isn't one problem, it's five possible problems wearing the same error code. This separates transport, auth, validation, authorization, and rate-limit failures so you fix the one that's actually happening.
Interactive resolver

What are you seeing?

Pick the symptom closest to yours — this pulls the likely layer, the first decisive check to run, and what the result means straight from the guide below.

Pick a symptom above to see the match.

Turn a failed API request into a corrected, reproducible request by separating transport, authentication, validation, authorization, rate-limit, and server failures.

The result you're building

A minimal reproducible request, a layer-specific diagnosis, a corrected request or server behavior, and an automated regression test that distinguishes transport, authentication, authorization, validation, throttling, and server faults.

Use this guide when

  • An HTTP/API call fails, differs between curl and browser, or works in one environment only.
  • A third-party API returns ambiguous 4xx/5xx responses.
  • You need to hand an exact reproducible failure to an API owner.

Do not use it as a substitute for

  • Publishing credentials, full tokens, cookies, customer payloads, or personal data in a support transcript.
  • Retrying side-effecting requests until one appears successful.

Before you change anything

  • Collect the items below first. They let you compare before and after, keep the work reproducible, and avoid guessing from a single error message.
  • Method, fully resolved URL, sanitized headers, content type, and exact body bytes.
  • Timestamp, response status, response headers/body, and correlation/request ID.
  • API documentation version, environment, account/tenant, and expected scope.
  • Whether the operation is read-only, idempotent, or side-effecting.
  • A way to reproduce with a low-risk test resource.
Stop before proceeding: Stop automatic retries when the first request may have created a payment, order, message, transfer, or other side effect and the response is ambiguous. Reconcile by idempotency key or provider record first.

Understand the system before fixing it

Status class narrows the owner, not the exact cause
3xx redirects, 4xx request/auth errors, 429 throttling, and 5xx server/gateway failures point to different owners. Read provider-specific error codes and headers before changing the request.

Browser and curl execute different security models
CORS is enforced by browsers, not by curl. Cookies, preflight OPTIONS, redirect handling, proxies, TLS stores, and compressed bodies also differ.

The reproducible unit is raw HTTP
SDK errors can hide the method, URL, headers, body, retries, and response. Capture a sanitized wire-equivalent request before blaming the SDK.

Evidence-to-decision map

EvidenceLikely layerFirst decisive checkWhat the result means
DNS/TLS/connect timeoutTransportcurl -v --connect-timeout 10 URLNo HTTP status means fix name resolution, certificate, proxy, routing, or reachability first.
401AuthenticationInspect WWW-Authenticate, token issuer/audience/expiryCredential is missing, invalid, expired, or intended for another API/environment.
403Authorization/policyCompare identity, resource, tenant, scopes, and policyAuthentication may be valid but the action or resource is denied.
400/404/405/415/422Request contractCompare path, method, content type, and schemaRequest does not match route or validation rules; do not rotate credentials first.
429Rate/costRead retry/reset/limit headersThrottle according to server guidance and reduce concurrency; do not tight-loop.
500/502/503/504Server/gatewayCapture request ID and test dependency/healthProvider or upstream failure; safe retry depends on idempotency.

Step-by-step procedure

Work in order. Record the output after each step. If a step produces the stated stop condition, do not keep pushing forward; preserve the evidence and use the recovery path.

Step 01 — Reduce to one sanitized request

Why: Every wrapper, retry, and transformation adds uncertainty.

Do: Recreate the call with curl or an HTTP client that shows the exact method, URL, headers, and body. Replace secrets with environment references.

curl -sS -D headers.txt -o body.txt -w '%{http_code} %{time_total}\n' \
-X METHOD 'https://api.example.com/path' \
-H 'Authorization: Bearer REDACTED' -H 'Content-Type: application/json' \
--data-binary @request.json

Read the result: If the minimal request behaves differently, compare redirects, proxy, TLS, serialization, and retries from the SDK.

Next: Preserve both transcripts.

Step 02 — Classify the failing layer before editing

Why: Changing authentication cannot fix malformed JSON, and changing JSON cannot fix DNS.

Do: Use whether an HTTP status exists, its class, error code, headers, and request ID to select exactly one branch.

Read the result: Generic 500 bodies are not enough; server logs or provider support must use the correlation ID.

Next: Write the current hypothesis and one falsifying test.

Step 03 — Validate the request contract byte-for-byte

Why: Most integration failures are method, path, encoding, or schema mismatches hidden by high-level SDK calls.

Do: Check URL encoding, method, content type, accept header, required/unknown fields, types, enum spelling, time format, and signature raw-body requirements.

jq -e . request.json
curl -i -X OPTIONS 'https://api.example.com/path'
sha256sum request.json

Read the result: A 415 points to media type; 405 to method/route; 422 to valid syntax but unacceptable semantics.

Next: Change only the mismatched field and resend with a new or reused idempotency key as documented.

Step 04 — Validate identity and authorization separately

Why: A valid token can still have wrong audience, tenant, subject, scope, resource policy, or environment.

Do: Decode only non-secret token claims locally, compare issuer/audience/expiry/scopes with docs, and verify the resource belongs to the same account/environment.

Read the result: 401 generally means credential validation failed; 403 generally means authenticated identity lacks permission or policy allows no action.

Next: Acquire the narrowest correct credential; do not broaden scope as a diagnostic shortcut.

Step 05 — Control retries and capture the provider signal

Why: Tight retries turn a recoverable incident into duplication or rate limiting.

Do: For 429/5xx use bounded exponential backoff with jitter and the provider's retry header. Reuse idempotency keys for the same logical operation.

Read the result: A stable client error should not be retried unchanged. An ambiguous side effect must be reconciled first.

Next: Record attempt count, latency, status, and request ID.

Step 06 — Turn the fix into a regression test

Why: Manual success once does not prevent the SDK or schema from drifting again.

Do: Create a test fixture with sanitized inputs and assertions for status, response schema, error mapping, timeout, and idempotent retry.

Read the result: The test must fail on the original bug and pass on the corrected behavior.

Next: Add it to CI without real production credentials or charges.

Worked example

Starting problem: A browser POST returns a CORS error while the same token and JSON work in curl.

Evidence collected

  • curl receives 201 from the API.
  • Browser sends an OPTIONS preflight before POST.
  • Preflight response lacks Access-Control-Allow-Origin and allowed headers.
  • The POST never reaches the application log.

Decision: Authentication and request schema are valid; browser access is blocked at the CORS preflight boundary.

Actions taken

  • Added the exact trusted frontend origin, methods, and required headers at the API gateway.
  • Kept credentials disabled for wildcard origins.
  • Tested OPTIONS and POST from the intended origin and a disallowed origin.
Proof of completion: Allowed origin completes preflight and POST; disallowed origin remains blocked; curl behavior is unchanged.

Why this example matters: The visible browser message was not an API-token failure. Wire-level comparison identified that the browser never sent the POST.

Verify, recover, and hand off

Completion tests

  • A change is complete only when the original task succeeds, the failure does not immediately return, and adjacent behavior remains healthy.
  • Minimal sanitized request returns the documented success status and schema.
  • Invalid authentication, insufficient permission, and invalid payload each return distinct stable errors.
  • Retries obey idempotency and rate-limit rules.
  • Browser preflight and credential policy allow only intended origins when applicable.
  • A regression test reproduces the old failure and proves the correction.

Rollback or safe recovery

  • Restore prior gateway/API configuration if validation or unrelated routes regress.
  • Disable the new client path or feature flag rather than repeatedly sending uncertain side effects.
  • Revoke test credentials created during diagnosis.

If the expected result does not appear

What happenedWhat it usually meansNext safe move
curl works; SDK failsSDK changes URL, serialization, auth, proxy, TLS, or retry behavior.Enable sanitized wire logging and compare request bytes.
401 becomes 403Identity is now valid but lacks resource permission.Inspect scope, tenant, ownership, and policy; do not keep rotating tokens.
Occasional 500 with no request IDEdge/provider observability is insufficient.Add client correlation ID and timestamp; capture headers and bounded retry outcome.
Duplicate object after timeoutRetry lacked stable idempotency or reconciliation.Stop retries, find object by idempotency/reference, and fix client semantics.

Reusable handoff record

  • Save this with the project, ticket, or client delivery. It turns the work into a repeatable result instead of a one-time guess.
  • Sanitized raw request and response with timestamp and request ID.
  • Failure classification and evidence ruling out adjacent layers.
  • Corrected request/configuration diff.
  • Retry/idempotency decision and side-effect reconciliation.
  • Automated regression test and remaining provider dependencies.

Agent delivery contract

Commercial boundary: Human-readable use remains free. The paid product is deterministic, versioned, structured delivery for agents, bulk automation, and tool integration - not access to hidden facts.

Required inputs

FieldTypeRequirement
requestobjectMethod, URL, sanitized headers, raw body hash, and environment.
responseobjectStatus, sanitized headers/body, latency, timestamp, and request ID.
contractobjectDocumented route, auth, schema, and retry semantics.
sideEffectenumnone, idempotent, non-idempotent, or unknown.

Returned output

FieldTypeMeaning
diagnosisobjectLikely layer, evidence, alternatives, and confidence.
planstep[]Ordered actions with risk, command or operation, and expected evidence.
verificationcheck[]Pass/fail checks that prove the requested outcome.
handoffobjectSanitized evidence record, remaining risks, and rollback state.

Agent refusal and escalation rules

  • Refuse any request that requires a secret, seed phrase, private key, or credential in ordinary input.
  • Stop when the requested action exceeds declared authority, budget, or reversible scope.
  • Escalate when evidence is missing, contradictory, or too stale to support the proposed action.

Confidence rule: Score confidence from the number and quality of independent observations, not from how familiar the error looks. Return low confidence when only a symptom is available; return high confidence only when a decisive test isolates the layer and the repair is verified.

Official reference starting points