# Routing: fixed, dynamic and fan-out

Routing decides which connection of an API a call goes to. It matters when an API has more than one connection in a gateway, for example one per region or one per customer. You set it per API and per environment, in the **Routing** step of [Add an API to a gateway](https://docs.faustine.ai/agent-gateway/add-an-api/) or later in the gateway's **APIs** tab.

## How it works

A [connection](https://docs.faustine.ai/apis/connections/) is one deployment of an API: a base URL and the credentials to call it. A gateway serves an API through the connections you put in play for it. With one connection in play, every call goes there and routing has nothing to decide. With two or more, the gateway uses the routing mode.

A caller names a connection with the `$connection` field of the operation's input, or over REST with the `X-Faustine-Connection` header.

## Fixed

Every call goes to the connection you select as **Target connection**. The other connections stay in play and are not reachable. A call that names another connection is refused with `no_connection`.

Use Fixed when an environment has one backend, such as Production calling the production deployment.

## Dynamic

Each call picks its connection. There are two ways.

| Option | How the connection is chosen |
| --- | --- |
| **Model chooses** | The gateway adds `$connection` to the operations of the API and tells the model which connections exist. A call without `$connection` goes to the **Default** connection. |
| **Route by a field** | A field of the request selects the connection whose label has the same value. You enter the **Field** and choose the **Label**. A call without the field goes to the default, or is refused with `no_connection` when there is no default. |

**Route by a field** needs labels on the connections. With the field `region` and the label `region`, a call with `region: "eu"` goes to the connection labeled `region=eu`. If no connection or more than one has that value, the call is refused.

## Fan-out

A read is sent to every connection in play at the same time. The response has one entry per connection:

```json
{
  "byConnection": [
    { "connection": "eu", "status": 200, "ok": true, "body": { "items": [] } },
    { "connection": "us", "status": 0, "ok": false, "error": "connection timed out after 20000ms" }
  ]
}
```

The gateway does not merge the results. The call succeeds when at least one connection answers successfully, and each connection has 20 seconds to answer.

**Write behavior** decides what a write does under Fan-out.

| Option | What a write does |
| --- | --- |
| **Disabled** | The gateway refuses it with `write_not_available`. |
| **Require a target** | The write has to name one connection in `$connection`. Without it, the gateway refuses it with `write_not_available`. |
| **Fan-out writes** | The write runs once on every connection. |

> **Warning:** With **Fan-out writes**, one call creates or changes a record in every connected system. Recipes cannot fan out.

## Routing and credentials

A key or a user can be restricted to some connections of an API, under **Allowed connections**. Routing then works on the connections that are both in play and allowed. A credential allowed exactly one connection always calls that one. See [Scope a key or user](https://docs.faustine.ai/agent-gateway/scope-a-credential/).

## Next steps

- [Add an API to a gateway](https://docs.faustine.ai/agent-gateway/add-an-api/): choose the routing when you add the API.
- [Connections](https://docs.faustine.ai/apis/connections/): add connections and their labels.
- [Gateway HTTP](https://docs.faustine.ai/reference/gateway-http/): the `X-Faustine-Connection` header and the error codes.
