News KrakenD CE v2.8 released with improved Lua and OpenTelemetry

Document updated on Dec 13, 2022

Returning the backend headers and errors

KrakenD’s default policy regarding errors and status codes is to hide from the client any backend details, this includes headers and errors, except when you use the no-op encoding.

The philosophy behind this is that clients have to be decoupled from their underlying services, as an API Gateway should do. The opposite is a reverse proxy or a simple router.

Strategies to return headers and errors

Yet, you can override the default policy of returning backend error details with different strategies.

  • Default strategy: Graceful degradation of the response (when using a non-no-op): Supports multiple backends (aggregation). HTTP status codes returned to the client are essentially 200 or 500, regardless of the backend(s) status codes. The body is built, merged, and manipulated from the working backends.
  • Headers and errors entirely handled by the backend (default strategy for no-op): Shows the HTTP status codes, headers, and body as returned by the backend (maximum one). You cannot manipulate data (except with plugins). This option is mostly a reverse proxy, and its usage is discouraged. Use no-op encoding.
  • Return the HTTP status code of a single backend. Sets an empty body when there are errors (obfuscation), but preserves the HTTP status codes of the backend. Use return_error_code (see below)
  • Return the HTTP status code and error body of a single backend. No obfuscation at all. Forwards the error body and the status code of a single backend. Use return_error_code and return_error_msg together (the latter is declared as a router option in the service level). The Content-Type from the backend is lost.
  • Return backend errors in a new key. Supports multiple backends. Like the graceful degradation option, but it add a new error key in the body when the backend fails -—ideal for debugging multiple backends. Use return_error_details (see below).
  • Show the error interpretation by the gateway but not the actual error body. Semi-obfuscation. The client sees an interpretation of the gateway like invalid status code, or context deadline exceeded but does not see the actual error delivered by the backend. The status code is always 200 or 500. Use return_error_msg (at the router level). The flag is also compatible with no-op.

The different combinations are exemplified below.

Return backend errors in a new key

If you prefer revealing error details to the client, you can show them in the gateway response. To achieve this, enable the return_error_details option in the backend configuration, and all errors will appear in the desired key.

Place the following configuration inside the backend configuration:

{
    "url_pattern": "/return-my-errors",
    "extra_config": {
        "backend/http": {
            "return_error_details": "backend_alias"
        }
    }
}

The return_error_details option sets an alias for this backend. When a backend fails, you’ll find an object named error_ + its backend_alias containing the detailed errors of the backend. If there are no errors, the key won’t exist.

An error example is:

{
    "error_backend_alias": {
        "http_status_code": 404,
        "http_body": "404 page not found\\n"
    }
}
All status are 200
When you use return_error_details, all status codes returned to the client are 200. The client must parse the response for the presence of the error_backend_alias or any other key you have set to determine if there’s a problem.

Example

The following configuration sets an endpoint with two backends that return its errors in two different keys:

{
        "endpoint": "/detail_error",
        "backend": [
            {
                "host": ["http://127.0.0.1:8081"],
                "url_pattern": "/foo",
                "extra_config": {
                    "backend/http": {
                        "return_error_details": "backend_a"
                    }
                }
            },
            {
                "host": ["http://127.0.0.1:8081"],
                "url_pattern": "/bar",
                "extra_config": {
                    "backend/http": {
                        "return_error_details": "backend_b"
                    }
                }
            }
        ]
    }

Let’s say your backend_b has failed, but your backend_a worked just fine. The client’s response could look like this:

{
    "error_backend_b": {
        "http_status_code": 404,
        "http_body": "404 page not found\\n"
    },
    "foo": 42
}

Return the HTTP status code of a single backend

When you have one backend only and use an encoding different than no-op, you can choose to return the original HTTP status code to the client.

The gateway obfuscates the HTTP status codes of the backend by default for many reasons, including security and consistency. Still, if you prefer using the HTTP status code of the backend instead, you can enable the return_error_code flag.

The body of the error will be empty unless you complement it with the return_error_msg at the router configuration (see below):

Place the following configuration in the configuration:

{
  "version": 3,
  "$schema": "http://www.krakend.io/schema/krakend.json",
  "extra_config": {
    "router": {
      "return_error_msg": true
    }
  },
  "endpoints": [
    {
      "endpoint": "/return-status-and-error",
      "backend": [
        {
          "url_pattern": "/404",
          "host": [
            "http://somehost"
          ],
          "extra_config": {
            "backend/http": {
              "return_error_code": true
            }
          }
        }
      ]
    }
  ]
}

Notice that the return_error_code and the return_error_details are mutually exclusive. You can use one or the other but not both. If you declare them together, the gateway will use only return_error_details.

Show an interpretation but not the error body

When you want to show the interpretation of the error but not the error of the backend, use the router option return_error_msg as follows:

{
  "version": 3,
  "$schema": "http://www.krakend.io/schema/krakend.json",
  "extra_config": {
    "router": {
      "return_error_msg": true
    }
  }
}

Contribute to KrakenD Documentation. Improve this page »

Scarf

Unresolved issues?

The documentation is only a piece of the help you can get! Whether you are looking for Open Source or Enterprise support, see more support channels that can help you.

See all support channels