# Router Options

> Explore the router options available in KrakenD API Gateway to customize the routing behavior and optimize API request handling

Source: https://www.krakend.io/docs/enterprise/service-settings/router-options/

The **optional router configuration** allows you to set global flags that change how KrakenD processes the requests globally at the router layer.

Generally speaking **you don’t need this**. But there is an exception in every case, and you might need to change some values.

## Configuration for the router

The `router` controls the behavior of KrakenD toward users. Its settings affect all activity in the gateway. For instance, you can **obfuscate the X-KrakenD-version header**, set a **custom body for 404 errors**, **remove the requests from the logs**, or define how to **calculate client IPs** to name a few examples.

To change the router behavior, you must add the namespace `router` inside the `extra_config` at the root of the configuration file. For instance:

```json
{
  "version": 4,
  "extra_config": {
    "router": {
       "hide_version_header": true
    }
  }
}
```

All the options you can set under `router` are:

##### Fields of Router Options

\* required fields

##### [`app_engine`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#app_engine "Click to copy link to app_engine") boolean

The app\_engine boolean trusts headers starting with X-AppEngine… for better integration with that PaaS.

##### [`auto_options`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#auto_options "Click to copy link to auto_options") boolean

When true, enables the autogenerated OPTIONS endpoint for all the registered paths

##### [`decompress_gzip`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#decompress_gzip "Click to copy link to decompress_gzip") integer

**Enterprise only.** Decompresses any Gzipped content before sending it to the backend when the `Content-Encoding` has `gzip` in the first position. You can also set this value [per endpoint](https://www.krakend.io/docs/enterprise/endpoints/maximum-request-size/).

Defaults to `0`

##### [`disable_access_log`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#disable_access_log "Click to copy link to disable_access_log") boolean

Stops registering access requests to KrakenD in the logs. You can still have a [Backend Log](https://www.krakend.io/docs/logging/#backend) if needed.

Defaults to `false`

##### [`disable_gzip`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#disable_gzip "Click to copy link to disable_gzip") boolean

**Enterprise only.** All the output to the end user on the Enterprise Edition uses gzip when accepted by the client. Use this flag to remove gzip compression.

Defaults to `false`

##### [`disable_handle_method_not_allowed`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#disable_handle_method_not_allowed "Click to copy link to disable_handle_method_not_allowed") boolean

Whether to checks if another method is allowed for the current route, if the current request can not be routed. If this is the case, the request is answered with Method Not Allowed and HTTP status code 405. If no other Method is allowed, the request is a 404.

##### [`disable_health`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#disable_health "Click to copy link to disable_health") boolean

When true you don’t have any exposed health endpoint. You can still use a TCP checker or build an endpoint yourself.

Defaults to `false`

##### [`disable_path_decoding`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#disable_path_decoding "Click to copy link to disable_path_decoding") boolean

Disables automatic validation of the url params looking for url encoded ones.

##### [`disable_redirect_fixed_path`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#disable_redirect_fixed_path "Click to copy link to disable_redirect_fixed_path") boolean

If true, the router tries to fix the current request path, if no handle is registered for it

##### [`disable_redirect_trailing_slash`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#disable_redirect_trailing_slash "Click to copy link to disable_redirect_trailing_slash") boolean

Disables automatic redirection if the current route can’t be matched but a handler for the path with (without) the trailing slash exists. Only works if `disable_redirect_fixed_path` is also set to true.

##### [`error_body`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#error_body "Click to copy link to error_body") object

Sets custom error bodies for 404 and 405 errors.

##### [`404`](#error_body-404 "Click to copy link to 404") object

Write any JSON object structure you would like to return to users when they request an endpoint not known by KrakenD. 404 Not Found errors.

##### [`405`](#error_body-405 "Click to copy link to 405") object

Write any JSON object structure you would like to return to users

##### [`forwarded_by_client_ip`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#forwarded_by_client_ip "Click to copy link to forwarded_by_client_ip") boolean

When set to true, the client IP will be parsed from the default request’s headers, or the custom ones (`remote_ip_headers`). If the IP has passed through a **trusted proxy** (e.g.: a proxy, load balancer, or a third party application) it will be extracted. If no IP can be fetched, it falls back to the IP obtained from the request’s remote address. When declared **you must** configure `trusted_proxies` too.

Defaults to `false`

##### [`gzip_profile`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#gzip_profile "Click to copy link to gzip_profile")

**Enterprise only.** Chooses the trade-off between compression ratio and CPU usage when gzipping the response to the end user. `speed` uses the fastest compression level, spending the least CPU per response and adding the least latency, but sending the largest payloads over the wire. `compression` uses the maximum level, producing the smallest payloads at the cost of noticeably more CPU and time per response, which pays off on large and highly repetitive bodies. `balanced` sits in between and is the right choice for most traffic. All three profiles emit standard gzip that any client decompresses the same way, so the profile only affects the size of the response and the resources needed to produce it. The setting has no effect when `disable_gzip` is `true`.

Possible values are: `"balanced"` , `"speed"` , `"compression"`

Defaults to `"balanced"`

##### [`health_path`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#health_path "Click to copy link to health_path") string

The path where you’d like to expose the health endpoint.

Defaults to `"/__health"`

##### [`hide_version_header`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#hide_version_header "Click to copy link to hide_version_header") boolean

Removes the version of KrakenD used in the X-KrakenD-version headers.

Defaults to `false`

##### [`logger_skip_paths`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#logger_skip_paths "Click to copy link to logger_skip_paths") array of strings

Defines the set of paths that are removed from the logging.

##### [`max_multipart_memory`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#max_multipart_memory "Click to copy link to max_multipart_memory") integer

Sets the maxMemory param that is given to http.Request’s Multipart Form method call.

##### [`max_payload`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#max_payload "Click to copy link to max_payload") integer

**Enterprise only.** Limits the maximum number of bytes a user can send to the gateway. `0` means no limit. You can also set this value [per endpoint](https://www.krakend.io/docs/enterprise/endpoints/maximum-request-size/).

Defaults to `0`

##### [`remote_ip_headers`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#remote_ip_headers "Click to copy link to remote_ip_headers") array of strings

List of headers used to obtain the client IP when `forwarded_by_client_ip` is set to `true` and the remote address is matched by at least one of the network origins of `trusted_proxies`.

##### [`remove_extra_slash`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#remove_extra_slash "Click to copy link to remove_extra_slash") boolean

A parameter can be parsed from the URL even with extra slashes.

Defaults to `false`

##### [`return_error_msg`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#return_error_msg "Click to copy link to return_error_msg") boolean

When there is an error in the gateway (such as a timeout, a non-200 status code, etc.) it returns to the client the reason for the failure. The error is written in the body as is.

Defaults to `false`

##### [`trusted_proxies`](https://www.krakend.io/docs/enterprise/service-settings/router-options/#trusted_proxies "Click to copy link to trusted_proxies") array of strings

List of network origins (IPv4 addresses, IPv4 CIDRs, IPv6 addresses or IPv6 CIDRs) from which to trust request’s headers that contain alternative client IP when `forwarded_by_client_ip` is `true`. When declared **you must** configure `forwarded_by_client_ip` set to `true`, and optionally `remote_ip_headers`.

Schema: [https://www.krakend.io/schema/v3.0/router.json](https://www.krakend.io/schema/v3.0/router.json "JSON schema definition")

## Return the real client IP

The flags `forwarded_by_client_ip`, `remote_ip_headers`, and `trusted_proxies` determine together how you get the client IP address.

Dependant flags

When your setup requires any attributes `forwarded_by_client_ip` or `trusted_proxies`, you **must declare both**. The attribute `remote_ip_headers` is only necessary when you want to overwrite the default headers.

### How the IP is retrieved internally

The flow the gateway follows to extract the client IP is as follows:

- The gateway fetches the IP from the connecting remote address
- Then it checks the IP from the headers listed under `remote_ip_headers`. When this list is not in the configuration, it looks in `X-Forwarded-For` and `X-Real-IP` (default lookup headers).
- Unless you have a single KrakenD exposed to the internet or working locally, the client request will travel through different relays. These relays generally modify the header to append where they received the request from (whether it is the originating client, a load balancer, another proxy, etc.). So, you usually have a comma-separated list of IPs in the header containing the IP as they travel from one relay to the other. For instance, if there is just one hop before KrakenD, the header the gateway sees could look like `X-Forwarded-For: 1.2.3.4,172.20.0.1` where `1.2.3.4` is the real IP of the user, and `172.20.0.1` the last relay seen.
- The list of `trusted_proxies` sets which IPs are part of these network hops, and **the last IP before a known trusted proxy** is the actual IP.
- If checking the trusted proxies does not work, it will return the remote address in the first step.

Here’s an example of behavior. Suppose the gateway receives a header `X-Forwarded-For: A,B,C,D` (IPs are expressed as letters for simplification). If your `trusted_proxies` configuration contains ranges for `C` and `D`, then the returned IP is `B`, as `A` could have been spoofed by the client.

**The real IP is stored in the `X-Forwarded-For` header that KrakenD uses.**

The following example shows a configuration that takes the user IP from an `X-Forwarded-For` header only, and the network origin has relays in the range `172.16.0.1/12` (IPv4 Private Address Space). The endpoint `/ip` returns the IP received. You can test this locally:

```json
{
  "$schema": "https://www.krakend.io/schema/v3.0/krakend.json",
  "version": 4,
  "echo_endpoint": true,
  "extra_config": {
      "router":{
          "forwarded_by_client_ip": true,
          "remote_ip_headers": [
            "X-Forwarded-For"
          ],
          "trusted_proxies": [
            "172.16.0.1/12"
          ]
      }
  },
  "endpoints": [
    {
      "endpoint": "/ip",
      "backend": [
        {
          "host": ["http://localhost:8080"],
          "url_pattern": "/__echo",
          "allow": ["req_headers.X-Forwarded-For"]
        }
      ]
    }
  ]
}
```

## Hide the version in the `X-KrakenD-version` header

You can remove the KrakenD version your installation uses by adding the `hide_version_header` flag as follows:

```json
{
  "version": 4,
  "extra_config": {
    "router": {
       "hide_version_header": true
    }
  }
}
```

The banner header will show an `undefined` version when the flag is set to `true`. To remove the header entirely, you must remove it in the CDN or layer in front of KrakenD.

## Custom JSON body for 404 and 405 errors

You can also define generic responses for 404 and 405 errors by defining the response object you will return to clients using the `error_body` property. Here is an example:

```json
{
  "version": 4,
  "extra_config": {
    "router": {
      "error_body": {
        "404": {
          "msg": "Unknown endpoint",
          "status": 404
        },
        "405": {
          "oh-my-god": "What on earth are you requesting?"
        }
      }
    }
  }
}
```

## Returning the gateway error message

The secure choice of KrakenD is that all errors generated at the gateway **are not returned to the client in the body**. By setting `return_error_msg` (*boolean*) to `true`, when there is an error in the gateway (such as a timeout, a non-200 status code, etc.), it returns the client the reason for the failure. The error is **written in the body as is**.

Gateway errors != backend errors

This option will return the gateway interpretation of the error (such as there was an *invalid status code*). Nevertheless, when this option is mixed with a backend flag [`return_error_code`](https://www.krakend.io/docs/enterprise/backends/detailed-errors/#showing-backend-errors) set to `true`, the backend error is returned, but its encoding is lost.

Consider using [`return_error_details`](https://www.krakend.io/docs/enterprise/backends/detailed-errors/#return-backend-errors-in-a-new-key) to create a key with the error and support aggregation, or just use `no-op` encoding if you need errors as returned by the backend.

```json
{
  "version": 4,
  "extra_config": {
      "router":{
          "return_error_msg":true
      }
}
```

## Remove requests from logs

There are two options to remove content from logs: the `logger_skip_paths` (list of paths you don’t want to see in the logs) and `disable_access_log`, which stops registering access requests.

```json
{
  "version": 4,
  "extra_config": {
      "router":{
          "logger_skip_paths":[
            "/__health"
          ],
          "disable_access_log": true
      }
}
```
