Gateway errors that help someone fix the problem
A blocked request is more useful when the error says what happened, where, and what to try next, without exposing sensitive details.
The idea in brief
A gateway in front of model APIs often rejects requests for good reasons: quotas, identity checks, content policies. A bare 403 Forbidden is accurate but leaves the caller guessing. Two public references help balance usefulness against security: the IETF's Problem Details standard and OWASP's error-handling guidance.
A standard shape for API errors
RFC 9457, Problem Details for HTTP APIs (2023), defines a JSON format served as application/problem+json. Its members are:
| Member | Meaning in the RFC |
|---|---|
type | A URI identifying the kind of problem |
title | A short summary that stays the same for that problem type |
status | The HTTP status code |
detail | An explanation of this occurrence, aimed at helping the client fix it |
instance | An identifier for this specific occurrence |
Problem types can add extension members. An illustrative quota rejection might look like this:
HTTP/1.1 429 Too Many Requests
Content-Type: application/problem+json
{
"type": "https://example.com/problems/token-quota",
"title": "Token quota exceeded",
"status": 429,
"detail": "This project used its hourly token quota. Retry after the reset or request a higher quota.",
"instance": "urn:request:4bf92f3577b34da6a3ce929d0e0e4736"
}
The instance value can carry the same trace ID used in the W3C traceparent header, so support can find the exact request.
What not to put in the error
Both sources warn against oversharing. RFC 9457's security section says to vet what goes into problem details and to avoid exposing implementation internals such as stack traces. OWASP's Error Handling Cheat Sheet recommends returning a generic message to the user and logging the details server side for investigation.
Read together, they suggest a split: the response names the problem type and a next step, while the detailed reason (which rule matched, internal component names) stays in the logs, reachable through the request ID.
Four questions as a design check
A good error answers four questions. They map onto the standard fairly directly:
- What happened?
typeandtitle. - Where did it happen? The problem type, for example gateway quota versus provider error.
- What can the caller change?
detail. - What should go to support?
instanceand a timestamp, never credentials or prompt content.
Limitations
Some policies should stay opaque.
For abuse or security rules, naming the exact rule can help someone work around it. OWASP's generic-message advice applies there.
Status codes still matter.
RFC 9457 notes that generic HTTP software usually ignores the status member, so the real HTTP status must be correct too.
Error copy needs maintenance.
Problem types are a small public contract. Changing them can break clients that rely on them.
Sources
Cite this post
Adam, Ammar. (Oct 2026). Gateway errors that help someone fix the problem. www.ammaradam.dev. https://www.ammaradam.dev/posts/gateway-errors-that-help/.
BibTeX
@article{adam2026gatewayerrorsthathelp,
title = {Gateway errors that help someone fix the problem},
author = {Adam, Ammar},
journal = {www.ammaradam.dev},
year = {2026},
month = {Oct},
url = {https://www.ammaradam.dev/posts/gateway-errors-that-help/}
}
Comments
Sign in with GitHub to like this post or join the discussion.