<!-- review: reviewed -->

<a id="http-docker"></a>

# Docker

Модуль обеспечивает динамическую настройку групп проксируемых серверов
как в [HTTP-](https://angie.software//angie/docs/configuration/modules/http/http_upstream.md#u-upstream), так и в [потоковых](https://angie.software//angie/docs/configuration/modules/stream/stream_upstream.md#s-u-upstream)
контекстах на основании Docker-меток контейнеров.
Для работы функции в группе должна быть настроена зона разделяемой памяти
(см. описание `zone` для [http](https://angie.software//angie/docs/configuration/modules/http/http_upstream.md#u-zone) и [stream](https://angie.software//angie/docs/configuration/modules/stream/stream_upstream.md#s-u-zone)).

#### NOTE
Модуль поддерживает работу как с Docker, так и с его аналогами,
например Podman, которые реализуют совместимый API.

Модуль подключается к демону Docker через API,
способ взаимодействия с которым задается директивой [docker_endpoint](#docker-endpoint).
Получив список запущенных контейнеров,
Angie анализирует их на наличие подходящих [меток](#docker-labels).
Если в описании контейнера присутствует метка с портом,
то адрес и порт такого контейнера,
а также параметры из других меток этого контейнера,
автоматически добавляются в соответствующий блок `upstream`
конфигурации Angie.

#### NOTE
Один и тот же контейнер можно добавить в несколько `upstream`-групп.
Для этого достаточно указать несколько наборов меток
с разными именами групп и портами.

Это особенно полезно,
если в контейнере работают несколько различных сервисов на разных портах —
каждый сервис можно ассоциировать со своей группой.

Затем модуль подписывается на события жизненного цикла контейнеров
и начинает обновлять конфигурацию проксируемых серверов без перезагрузки Angie:

- при запуске контейнера с подходящими метками
  его внутренний IP-адрес добавляется в заданную группу;
- при остановке или удалении контейнера
  он автоматически удаляется из группы;
- при приостановке контейнера командой **docker pause**
  сервер помечается как `down`,
  а при **docker unpause** — как `up`.

<a id="configuration-example-12"></a>

## Пример конфигурации

Директивы самого модуля всегда находятся в контексте `http`,
но группы проксируемых серверов могут быть определены
как в контексте `http`, так и в потоковом контексте `stream`.

Пример конфигурации для `http`:

```nginx
http {

    # Примеры вариантов подключения:
    # docker_endpoint http://127.0.0.1:2375;
    # docker_endpoint https://127.0.0.1:2376;
    docker_endpoint unix:/var/run/docker.sock;

    # максимальный размер буфера ответа Docker (необязательно)
    # docker_max_object_size 128k;

    upstream u {

        zone z 1m; # необходима зона разделяемой памяти
    }

    server {

        listen 80;
        server_name example.com;

        location / {

            proxy_pass http://u;
        }
    }
}
```

Аналогично в потоковом контексте:

```nginx
http {

    # Примеры вариантов подключения:
    # docker_endpoint http://127.0.0.1:2375;
    # docker_endpoint https://127.0.0.1:2376;
    docker_endpoint unix:/var/run/docker.sock;

    # максимальный размер буфера ответа Docker (необязательно)
    # docker_max_object_size 128k;
}

stream {

    upstream u {

        zone z 1m;
    }

    server {

        listen 12345;
        proxy_pass u;
    }
}
```

Получив событие для контейнера,
Angie ищет метки вида
`angie.http.upstreams.<имя>.port=<порт>` (для HTTP-контекста)
или `angie.stream.upstreams.<имя>.port=<порт>` (для потокового контекста).
При наличии метки адрес контейнера в указанной Docker-сети
(или первой доступной, если метка `angie.network` не задана)
добавляется в соответствующую группу проксируемых серверов.

Если контейнер останавливается или удаляется, сервер убирается из группы;
если контейнер приостанавливается, сервер помечается как `down`.

Фрагмент файла `docker-compose.yml` с метками, которые распознает Angie:

```yaml
services:
  myapp:
    image: myapp:latest
    labels:
      - "angie.http.upstreams.u.port=8080"
      - "angie.network=my_bridge"
      - "angie.http.upstreams.u.weight=2"
      - "angie.http.upstreams.u.max_conns=50"
      - "angie.http.upstreams.u.max_fails=3"
      - "angie.http.upstreams.u.fail_timeout=10s"
      - "angie.http.upstreams.u.backup=true"
```

<a id="docker-labels"></a>

## Метки

Метки задают параметры сервера в группе проксируемых серверов
аналогично аргументам директивы `server`:

| Метка                                                               | Назначение                                                                                                      |
|---------------------------------------------------------------------|-----------------------------------------------------------------------------------------------------------------|
| `angie.(http|stream).upstreams.<имя>.port=<порт>`  *(обязательная)* | Порт контейнера, по которому будет обращаться Angie;<br/>: сам контейнер добавляется в группу с именем `<имя>`. |
| `angie.network=<docker-network>`                                    | Имя Docker-сети, из которой следует брать IP-адрес контейнера.                                                  |
| `angie.(http|stream).upstreams.<имя>.weight=<n>`                    | Значение параметра `weight`.                                                                                    |
| `angie.(http|stream).upstreams.<имя>.max_conns=<n>`                 | Максимальное число одновременных соединений (`max_conns`).                                                      |
| `angie.(http|stream).upstreams.<имя>.max_fails=<n>`                 | Порог неудачных попыток (`max_fails`).                                                                          |
| `angie.(http|stream).upstreams.<имя>.fail_timeout=<t>`              | Интервал для подсчета неудачных попыток (`fail_timeout`).                                                       |
| `angie.(http|stream).upstreams.<имя>.backup=true|false`             | Помечает сервер как `backup`.                                                                                   |
| `angie.(http|stream).upstreams.<имя>.sid=<строка>`                  | Устанавливает пользовательский идентификатор сервера (`sid`),<br/>для проксируемого сервера.                    |
| `angie.(http|stream).upstreams.<имя>.slow_start=<время>`            | Включает режим `slow_start` с настраиваемым периодом времени.                                                   |

<a id="directives-13"></a>

## Директивы

<a id="index-0"></a>

<a id="docker-endpoint"></a>

### docker_endpoint

| [Синтаксис](https://angie.software//angie/docs/configuration/configfile.md#configfile)   | `docker_endpoint` `URL`;   |
|------------------------------------------------------------------------------------------|----------------------------|
| По умолчанию                                                                             | —                          |
| [Контекст](https://angie.software//angie/docs/configuration/configfile.md#configfile)    | http                       |

Указывает способ подключения к демону Docker и включает отслеживание
событий контейнеров.
Поддерживаются следующие варианты:

| `unix:/var/run/docker.sock`             | Подключение через Unix-сокет (например, `/var/run/docker.sock`).   |
|-----------------------------------------|--------------------------------------------------------------------|
| `http://host:port`, `https://host:port` | Подключение по HTTP или HTTPS к удаленному Docker API.             |

Подключение можно дополнительно настроить с помощью контекста [client](https://angie.software//angie/docs/configuration/modules/http/index.md#client),
куда модуль добавляет два именованных `location`:

- `@docker_events` используется для получения событий контейнеров;
- `@docker_containers` — для получения информации о контейнерах.

По умолчанию в них задана директива [proxy_pass](https://angie.software//angie/docs/configuration/modules/http/http_proxy.md#proxy-pass)
с адресом подключения и рядом других оптимальных настроек по умолчанию,
к которым можно добавить другие настройки из модуля [Proxy](https://angie.software//angie/docs/configuration/modules/http/http_proxy.md#http-proxy).

Если директива задана,
Angie открывает соединение с Docker указанным способом,
запрашивает список запущенных контейнеров,
анализирует их метки и обрабатывает все последующие события контейнеров,
добавляя или удаляя серверы в группах проксируемых серверов согласно меткам.

<a id="index-1"></a>

<a id="docker-max-object-size"></a>

### docker_max_object_size

| [Синтаксис](https://angie.software//angie/docs/configuration/configfile.md#configfile)   | `docker_max_object_size` `<размер>`;   |
|------------------------------------------------------------------------------------------|----------------------------------------|
| Значение по умолчанию                                                                    | `64k`                                  |
| [Контекст](https://angie.software//angie/docs/configuration/configfile.md#configfile)    | http                                   |

Задает максимальный размер буфера,
который используется как для JSON-ответов на запросы к Docker,
так и для потока событий контейнеров.

- Для обычных запросов (версия API, список контейнеров, информация о контейнере):
  весь ответ должен поместиться в буфер, иначе возникнет ошибка.
- Для событий контейнеров используется потоковая обработка
  с переиспользованием буфера,
  что позволяет обрабатывать неограниченный поток событий.

Типовое значение `64k` достаточно примерно для 25 контейнеров.

При возникновении ошибок подключения к Docker API или обработки ответов
модуль автоматически повторяет попытки через определенные интервалы времени.
Максимальное количество повторных попыток для получения информации
о конкретном контейнере ограничено двумя  *дополнительными* попытками;
после этого модуль прекращает попытки для данного контейнера.
