Обратный прокси Traefik: статическая конфигурация
Продолжение статьи про обратный прокси Traefik. Для полного понимания рекомендую прочитать сначала предыдущую.
В этой статье мы разберем статическую конфигурацию Traefik. Она включает в себя такие настройки как entryPoints, providers, certificatesResolvers, logs. Файл статической конфигурации (traefik.yaml) является единым и содержит все базовые инструкции для запуска Traefik. Ниже я привожу свою конфигурацию, которую использую прямо сейчас у себя.
Статическая конфигурация Traefik
global:
checkNewVersion: true
sendAnonymousUsage: false
api:
dashboard: true
insecure: false
debug: false
entryPoints:
websecure:
address: :443
asDefault: true
http:
tls:
certResolver: timewebcloud
forwardedHeaders:
trustedIPs:
- 10.0.0.1/32
proxyProtocol:
trustedIPs:
- 10.0.0.1/32
providers:
file:
directory: /etc/traefik/dynamic
watch: true
certificatesResolvers:
timewebcloud:
acme:
caServer: https://acme-v02.api.letsencrypt.org/directory
email: roman.kvasnikov@gmail.com
storage: /etc/traefik/acme.json
dnsChallenge:
provider: timewebcloud
resolvers:
- 8.8.8.8:53
- 8.8.4.4:53
log:
filePath: /var/log/traefik/traefik.log
level: WARN
compress: true
accessLog:
filePath: /var/log/traefik/access.log
addInternals: true
bufferingSize: 100
fields:
names:
StartUTC: drop
Я не буду досконально расписывать каждый параметр в этой конфигурации потому что описание любого из них, можно найти за секунды в официальной документации обратного прокси Traefik. Затрону лишь некоторые важные из них, о чем хотелось бы рассказать.
1. entryPoints
В моей конфигурации определена единственная точка входа — websecure, которая прослушивает только порт 443 (HTTPS).
Это единственный открытый порт в LXC-контейнере с Traefik (не считая SSH порта). Все сервисы моего домашнего сервера доступны исключительно по HTTPS через поддомены. Другие порты не используются.
Note
В статье Организация внешнего доступа к домашней Homelab, я упоминал, что мы открываем два порта, - 80 (HTTP) и 443 (HTTPS). Но, если используется DNS-01 challenge (о нём ниже), то порт 80 не требуется вовсе. Весь трафик работает исключительно через HTTPS.
Указываем параметр asDefault: true делая эту точку входа по умолчанию, чтобы потом не нужно было ее указывать явно для каждого маршрута.
Тоже самое делаем и для certResolver. О его конфигураци написано чуть ниже. Тут просто указываем его также, по умолчанию.
Дополнительно я указал, что Traefik доверяет входящим подключениям только от нашего внешнего VPS, соединённого с ним через WireGuard-туннель. Поэтому в параметрах forwardedHeaders.trustedIPs и proxyProtocol.trustedIPs указан доверенный IP-адрес из подсети WireGuard — 10.0.0.1/32.
Параметр forwardedHeaders позволяет принимать и доверять заголовкам вида X-Forwarded-*, которые передаются проксирующей стороной (в данном случае VPS) и также используются для определения исходного IP-адреса и других параметров запроса.
Параметр proxyProtocol необходим для корректного определения реального IP-адреса клиента. Без его настройки Traefik видел бы все входящие подключения как поступающие только от IP-адреса VPS (10.0.0.1), а не от фактического клиента.
Note
proxyProtocolбудет работать только если VPS действительно отправляет Proxy Protocol (например, через Nginx с proxy_protocol). В статье Организация внешнего доступа к домашней Homelab мы указалиproxy_protocol, так что если вы делаете точно также - все будет работать.
2. providers
Здесь мы указываем путь до каталога с файлами динамической конфигурации. А также указываем флаг watch: true, чтобы изменения вступали в силу сразу же после изменения файлов без перезапуска Traefik.
3. certificatesResolvers
В данном фрагменте настраивается механизм автоматического получения SSL-сертификатов через протокол ACME от центра сертификации Let's Encrypt. Тут я создаю резолвер сертификатов и называю его timewebcloud. Имя произвольное, я назвал его по названию своего провайдера, через который я буду подтверждать факт владения доменом. Этот резолвер я указал чуть выше в конфигурации для точки входа websecure по умолчанию. Теперь этот резолвер применится ко всем нашим роутерам автоматически.
Настраиваем сам протокол ACME. Указываем:
- Адрес ACME сервера Let's Encrypt.
- Email адрес для регистрации ACME аккаунта и получения уведомлений об истечении действия сертификатов или проблемах с их продлением.
- Файл для хранения сертификатов и ключей. Важно чтобы он имел права доступа 600, так как содержит приватные ключи.
Дальше указываем, что метод подтверждения владения доменом у нас будет DNS-01 challenge. Это означает, что при выпуске сертификата Traefik автоматически создаёт специальную TXT-запись в DNS-зоне домена. Let's Encrypt проверяет наличие этой записи и, если всё корректно, выпускает сертификат.
Преимущества DNS-challenge:
- не требуется открытый порт 80 (HTTP);
- можно выпускать wildcard-сертификаты (*.example.com), чтобы не выпускать несколько сертификатов для каждого сервиса;
- не зависит от прямой доступности сервера из интернета.
Запись provider: timewebcloud означает, что Traefik будет работать с DNS-API провайдера Timeweb Cloud для автоматического создания и удаления TXT-записей. Для этой возможности в файле .env мы определяем переменную окружения TIMEWEBCLOUD_AUTH_TOKEN. Найти свой провайдер и посмотреть какие для него нужны переменные окружения можете здесь: https://go-acme.github.io/lego/dns/index.html
Ну и наконец я указал два публичных DNS резолвера от Google для проверки доступности TXT-записи во время ACME challenge.
Подытожим:
- Traefik автоматически получает и продлевает сертификаты Let's Encrypt.
- Подтверждение владения доменом происходит через DNS-01 challenge.
- TXT-записи создаются через API Timeweb Cloud.
- Сертификаты и ключи хранятся локально в acme.json.
- Проверка доступности TXT-записи DNS выполняется через публичные DNS-резолверы Google.
4. log
В этом разделе настраиваются системные логи Traefik — ошибки, предупреждения и служебные сообщения. Здесь задаётся путь к файлу журнала, уровень логирования и автоматическое сжатие архивных логов.
Конфигурация интуитивно понятна. Подробное описание всех доступных параметров можно найти в официальной документации Traefik.
5. accessLog
В данном разделе настраивается журнал входящих HTTP-запросов — информация о том, кто обращался к серверу, к какому ресурсу и с каким результатом (статус ответа).
Access-лог особенно важен, если сервер доступен из интернета. Он позволяет:
- анализировать входящий трафик;
- выявлять подозрительную активность;
- обнаруживать попытки перебора, сканирования и другие несанкционированные обращения.
Если сервер доступен исключительно из доверенной локальной сети, необходимость в подробном access-логе может быть не столь критичной. Однако при открытии внешнего доступа его ведение фактически становится обязательным. Именно на основе этих логов можно настраивать системы защиты и блокировать нежелательные источники (например, автоматические сканеры — подробнее об этом в отдельной статье).
Запуск Traefik как systemd сервиса
В предыдущей статье был рассмотрен процесс установки Traefik через бинарный файл. После создания статической конфигурации необходимо запустить сервис и добавить его в автозагрузку systemd.
systemctl daemon-reload # Перечитываем unit-файлы systemd после создания traefik.service
systemctl start traefik # Запускаем сервис Traefik
systemctl enable traefik # Добавляем сервис в автозагрузку
systemctl status traefik # Проверяем текущий статус сервиса
journalctl -u traefik -f # Просмотр логов Traefik в реальном времени
После изменения статической конфигурации, нам нужно всегда перезапускать сервис Traefik, чтобы изменения вступили в силу:
systemctl restart traefik
В следующей статье мы затронем динамическую конфигурацию, настройку роутеров, сервисов и middlewares.