# Configuration Structure

> Learn about the configuration structure and organization in KrakenD API Gateway to effectively define the behavior of your API gateway

Source: https://www.krakend.io/docs/configuration/structure/

All KrakenD behavior depends on its configuration file(s). You’ll find it referenced through all this documentation and for simplicity as the `krakend.json`, although the configuration [supports formats other than JSON](https://www.krakend.io/docs/configuration/supported-formats/) and it can be described [using multiple files and templates](https://www.krakend.io/docs/configuration/flexible-config/). Being familiar with its structure it’s essential.

The correctness of a configuration file is determined by the [check](https://www.krakend.io/docs/configuration/check/) and [audit](https://www.krakend.io/docs/configuration/audit/) commands using different perspectives.

## Configuration file structure

There are a large number of options you can put in this file. Let’s focus now only on the main structure:

```json
{
    "$schema": "https://www.krakend.io/schema/v3.0/krakend.json",
    "version": 4,
    "endpoints": [],
    "extra_config": {}
}
```

- `$schema`: *Optional* but recommended. When added, enables [IDE integration](https://www.krakend.io/docs/developer/ide-integration/) with autocompletion and documentation. Defines the JSON schema to validate your configuration. The KrakenD linting process (`krakend check --lint`) does not read this property as it knows which version must use on runtime.
- `version` (*mandatory*): The version of the configuration file format (not the version of KrakenD). KrakenD refuses to start when the value doesn’t match the format it expects.
  
  - Format version `4`: **Current** (since `v3.0`)
  - Format version `3`: For versions between `v2.0` and `v2.13`. KrakenD `v3.0` and later refuse it with `unsupported version: 3 (want: 4)`.
  - Format version `2`: Deprecated in 2022, for versions between `v0.4` and `v1.4.1`
  - Format version `1`: Deprecated in 2016, for versions `v0.3.9` and older.
- `endpoints[]`: An array of [endpoint objects](https://www.krakend.io/docs/endpoints/) offered by the gateway and all the associated backends and configurations. This is your API definition.
- `extra_config{}`: Service components’ configuration. Whatever is not a core functionality of the [Lura Project](https://luraproject.org) is declared in a unique **namespace** (a key) in the configuration, so that you can configure multiple elements without collisions.

### The `endpoints` structure

Inside the `endpoints`, you declare an array with [endpoint objects](https://www.krakend.io/docs/endpoints/). Every object has an `endpoint` (the URL) the gateway offers to users. For each endpoint, you need to declare at least one `backend` (the data origin).

It looks like this:

```json
{
    "endpoints": [
        {
          "endpoint": "/v1/foo-bar",
          "backend": [
            {
              "url_pattern": "/foo",
              "host": [
                "https://my.foo-api.com"
              ]
            },
            {
              "url_pattern": "/bar",
              "host": [
                "https://my.bar-api.com"
              ]
            }
          ]
        }
      ]
}
```

The configuration above declares an endpoint `/v1/foo-bar`, which returns the result of merging the responses from two backends `https://my.foo-api.com/foo` and `https://my.bar-api.com/bar`. These two calls execute in parallel.

That’s the basic structure of endpoints; for more information see [how to create endpoints](https://www.krakend.io/docs/endpoints/).

### The `extra_config` structure

KrakenD is very modular and comes bundled with many components that extend the core functionality of the [Lura Project](https://luraproject.org). The `extra_config` stores each component configuration that is not handled by Lura itself.

Components declare in their source code a **unique namespace**. KrakenD registers the component during the startup, and it passes to the component the configuration found under a key matching the **namespace** inside the `extra_config` object.

```json
    {
        "extra_config": {
          "component-1-namespace": {
            "some": "config"
          },
          "component-2-namespace": {
          }
        }
    }
```

For instance, the [extended logging component](https://www.krakend.io/docs/logging/) uses the **namespace** `telemetry/logging`:

```json
{
    "version": 4,
    "extra_config": {
        "telemetry/logging": {
          "level": "WARNING",
          "prefix": "[KRAKEND]",
          "stdout": true
        }
    }
}
```

### Placements for the `extra_config`

The `extra_config` can appear in the root of the file and on other placements (or levels) as well. It depends entirely on **the scope** of every component and the nature of its functionality.

An `extra_config` in the **root level** usually sets functionalities with a **service scope**: these influence the gateway globally and on every request (e.g., metrics). On the other hand, `extra_config` placed more profound in the configuration affects a tinier scope. An example could be a configuration that is loaded when a certain endpoint is called.

All components will seek the `extra_config` in its defined scope. The possible placements of the `extra_config` are:

- `service` (root level)
- `endpoint`
- `backend`

For instance, you might want to set a [rate limit](https://www.krakend.io/docs/throttling/) between a user and a `/my-rate-limited` endpoint in KrakenD. And for that, you would place the `extra_config` inside that `endpoint` scope. Or you might want to limit the connections between a KrakenD endpoint against your services; then you would place the `extra_config` in the `backend` scope.

**You don’t have to guess where to put the `extra_config`** . Each component has in the documentation what is the scope(s) is built for.

### Example

The following code is an example defining two simultaneous [rate limiting strategies](https://www.krakend.io/docs/throttling/): A limit of 5000 reqs/second for a specific endpoint, but yet, one of its backends accepts a maximum of 100 reqs/s. When the backend limit is reached, the user will have partial responses, and when both are surpassed the user won’t have data from any of the backends.

Notice how `extra_config` is present in the endpoints and backend scopes.

```json
{
  "version": 4,
  "endpoints": [
    {
      "endpoint": "/limited-to-5000-per-second",
      "extra_config": {
        "qos/ratelimit/router": {
          "max_rate": 5000
        }
      },
      "backend": [
        {
          "host": [
            "http://slow.backend.com/"
          ],
          "url_pattern": "/slow/endpoint",
          "extra_config": {
            "qos/ratelimit/proxy": {
              "max_rate": 100,
              "capacity": 1
            }
          }
        },
        {
          "host": [
            "http://fast.backend.com/"
          ],
          "url_pattern": "/fast/endpoint"
        }
      ]
    }
  ]
}
```

For larger sample files with more options you can have a look a the [KrakenD Playground](https://www.krakend.io/docs/overview/playground/).
