Safeguard
Security Guides•

What should a GraphQL API return when a query fails in production?

GraphQL errors can leak stack traces and internals. Here is what to return to clients, what to log server side, and how to check your error settings today.

Safeguard Security Team
4 min read

Return a short, generic message and a stable error code, and keep the detail in your server logs. Production GraphQL APIs should not return stack traces or run in debug mode. OWASP lists excessive error messages among the insecure defaults to change, because they teach an attacker how your server works.

Why errors are a leak

A GraphQL response can carry an errors array even when the HTTP status is a success. Servers often fill it with whatever the exception said: a file path, a SQL fragment, a library version, an internal service name. Each one shortens an attacker's research.

OWASP's GraphQL cheat sheet says production APIs should not return stack traces or be in debug mode, and notes that the way to do it is implementation specific. Middleware that formats errors is one popular approach. The cheat sheet gives one example: with one common server library you pass an option that turns off stack traces in error responses.

The same cheat sheet advises rejecting invalid input gracefully, being careful not to reveal excessive information about how the API and its validation work.

What clients need, what logs need

FieldClient responseServer log
Short human messageYes, genericYes
Stable error codeYesYes
Stack traceNoYes
SQL or file pathNoYes, if safe to store
Request IDYesYes
User or tenant IDNoYes

The request ID is the bridge. A user can quote it to support, and an engineer can find the full detail in logs without the user ever seeing it.

Steps to fix

  1. Find your error formatter or equivalent hook in the GraphQL server library you use.
  2. Map known, safe errors to explicit codes such as UNAUTHENTICATED, FORBIDDEN and BAD_USER_INPUT.
  3. Replace everything else with a generic internal error message plus a request ID.
  4. Turn off debug mode and stack trace output in production configuration, not just in code defaults.
  5. Make sure validation errors do not echo schema details beyond what a client needs. Related risk: field suggestions, covered in this post on introspection and suggestions.
  6. Log the detail server side with sensitive values removed.
  7. Test by causing failures on purpose in a staging environment: a malformed query, a missing field, a resolver exception, a database timeout. Read each response.

Common traps

Resolver exceptions from a database driver often include query text. Third party API failures may include URLs and tokens in their messages. Frameworks sometimes add an extensions object with debugging data. Check all three.

Also look at partial responses. GraphQL can return some data plus errors for the rest. Make sure fields that failed authorization return the same shape of error as fields that do not exist, so the response does not confirm that a hidden field is real.

Finally, separate logging from responses in your tests. A common mistake is to fix the response and leave the verbose error in a log that many people can read. Treat log access as a control too.

Try it yourself

Click through it at your own pace, or open it full screen.

Look for findings about verbose errors or information disclosure and note how they are described.

Quick check

Is it fine to show full errors in staging?

Usually yes, but staging is often reachable from the internet and holds real looking data. Apply the same rules unless the environment is private.

How do I help users report an error without leaking detail?

Return a request ID in the response. Support can quote it and engineers can find the full detail in logs.

Safeguard scans your dependencies and SBOMs for known vulnerabilities, including GraphQL server libraries, so you can patch the code that formats these errors. A free scan is at gold.safeguard.sh/scan.

Sources

Last reviewed: 19 October 2026.

Never miss an update

Weekly insights on software supply chain security, delivered to your inbox.

Self-healing security runs on Safeguard.

Your first fix PR is minutes away.

No sales call required, even your agent can complete the purchase over MCP.