Веб-интерфейсы систем хранения и виртуализации, таких как TrueNAS и Proxmox VE, часто становятся первостепенной целью для атак. Их стандартная аутентификация по логину и паролю уязвима к брутфорсу и фишингу. Это руководство показывает, как добавить второй фактор защиты, используя Nginx в качестве аутентификационного шлюза и Authelia как центральный сервис авторизации. Вы получите готовые конфигурации Nginx для обеих платформ и пошаговые инструкции по настройке TOTP. Решение не требует модификации исходного кода TrueNAS или Proxmox и позволяет централизованно управлять доступом к нескольким панелям.
Почему стандартной защиты веб-панелей недостаточно
Встроенная аутентификация TrueNAS Core/Scale и Proxmox VE не поддерживает двухфакторную аутентификацию (2FA) из коробки. Пароль, даже сложный, остается единым фактором. Если он будет скомпрометирован, злоумышленник получит полный контроль над системой хранения данных или виртуальной инфраструктурой. Централизованный подход через обратный прокси решает три ключевые проблемы: устраняет единую точку отказа в виде одного пароля, предоставляет единую точку входа для аудита и позволяет гибко управлять политиками доступа для разных сервисов.
Архитектура решения строится на принципе делегирования аутентификации. Nginx выступает в роли обратного прокси и шлюза. Для каждого запроса к защищенному ресурсу (например, https://nas.your-domain.com) модуль ngx_http_auth_request_module делает внутренний подзапрос к отдельному сервису авторизации (Authelia). Только после успешной проверки логина, пароля и одноразового кода TOTP Nginx проксирует исходный запрос к настоящему веб-интерфейсу TrueNAS или Proxmox. Для конечного приложения этот процесс прозрачен.
Как работает аутентификация через обратный прокси: схема auth_request
Поток запроса выглядит так:
- Пользователь запрашивает доступ к защищенной панели (TrueNAS).
- Nginx перехватывает запрос и проверяет, есть ли у пользователя валидная сессия.
- Если сессии нет, Nginx возвращает код 401 и перенаправляет пользователя на страницу входа Authelia.
- Пользователь вводит логин, пароль и код из приложения-аутентификатора (Google Authenticator).
- Authelia проверяет учетные данные и TOTP. При успехе устанавливает cookie сессии и возвращает Nginx код 200.
- Nginx, получив успешный ответ от Authelia, проксирует исходный запрос к веб-интерфейсу TrueNAS, передавая оригинальные заголовки, включая
X-Forwarded-ForиHost. - Пользователь получает доступ к панели управления.
Главное преимущество схемы – отсутствие необходимости изменять конфигурацию или код самого TrueNAS или Proxmox. Весь контроль доступа вынесен на уровень веб-сервера.
Выбор и подготовка компонентов: Authelia как сердце системы 2FA
Для реализации централизованной 2FA подходят несколько решений: Authelia, Vouch Proxy и OAuth2 Proxy. Authelia выбран для этого руководства, так как это самостоятельный, полнофункциональный сервер аутентификации с поддержкой TOTP, push-уведомлений (через Duo) и возможностью интеграции с LDAP/Active Directory. Он не зависит от внешних OAuth-провайдеров и может работать в изолированном окружении.
Перед началом убедитесь, что на сервере (это может быть отдельная виртуальная машина или тот же хост, где работает Nginx) установлены Docker и Docker Compose. Рекомендуется выделить для Authelia отдельный субдомен, например, auth.your-domain.com, и защитить его SSL-сертификатом. Для получения и автоматического обновления бесплатных сертификатов Let's Encrypt используйте Certbot или решение вроде Nginx Proxy Manager. Подробнее о настройке полноценного защищенного веб-сервера можно прочитать в нашем практическом руководстве по защите Nginx и Apache.
Установка и базовая конфигурация Authelia в Docker
Создайте структуру каталогов и файлов для Authelia:
mkdir -p /opt/authelia/config
cd /opt/authelia
Создайте файл docker-compose.yml:
version: '3.8'
services:
authelia:
image: authelia/authelia:latest
container_name: authelia
volumes:
- ./config:/config
ports:
- "9091:9091"
environment:
- TZ=Europe/Moscow
restart: unless-stopped
networks:
- authelia-network
networks:
authelia-network:
driver: bridge
Основная конфигурация хранится в /opt/authelia/config/configuration.yml. Минимальный рабочий пример для начала:
host: 0.0.0.0
port: 9091
log:
level: info
jwt_secret: your_super_secret_jwt_key_change_me # Сгенерируйте надежный ключ
default_redirection_url: https://nas.your-domain.com
server:
read_buffer_size: 4096
write_buffer_size: 4096
enable_pprof: false
enable_expvars: false
disable_keepalive: false
theme: dark
session:
name: authelia_session
secret: another_super_secret_session_key_change_me # Еще один уникальный ключ
expiration: 1h
inactivity: 5m
domain: your-domain.com
storage:
local:
path: /config/users_database.yml
authentication_backend:
file:
path: /config/users_database.yml
password:
algorithm: argon2id
iterations: 1
salt_length: 16
parallelism: 8
memory: 128
access_control:
default_policy: deny
rules:
- domain: "nas.your-domain.com"
policy: two_factor
- domain: "pve.your-domain.com"
policy: two_factor
regulation:
max_retries: 5
find_time: 2m
ban_time: 10m
notifier:
filesystem:
filename: /config/notifications.txt
После создания конфигурации запустите Authelia: docker-compose up -d. Убедитесь, что сервис доступен: curl http://localhost:9091/api/health должен вернуть статус OK.
Настройка двухфакторной аутентификации TOTP в Authelia
TOTP (Time-based One-Time Password) генерирует одноразовые 6-значные коды, которые меняются каждые 30 секунд. Для работы нужен секретный ключ, общий для сервера Authelia и мобильного приложения пользователя (Google Authenticator, Authy).
Сначала добавьте пользователя в файл /opt/authelia/config/users_database.yml. Пароль должен быть хэширован с помощью утилиты authelia crypto hash generate, входящей в образ Docker. Запустите команду внутри контейнера:
docker exec authelia authelia crypto hash generate --password 'YourStrongPassword'
Скопируйте полученный хэш и создайте файл users_database.yml:
users:
admin:
displayname: "Администратор"
password: "$argon2id$v=19$m=128,t=1,p=8$c2FsdF9leGFtcGxl$your_hashed_password_here"
email: admin@your-domain.com
groups:
- admin
Перезапустите Authelia: docker-compose restart. Теперь откройте в браузере https://auth.your-domain.com. После ввода логина и пароля система предложит отсканировать QR-код для настройки TOTP. Используйте для этого любое приложение-аутентификатор. После успешной привязки каждый вход будет требовать как пароль, так и текущий 6-значный код из приложения.
Конфигурация Nginx как аутентификационного шлюза
Убедитесь, что в вашем Nginx собран модуль ngx_http_auth_request_module. Проверить можно командой nginx -V 2>&1 | grep -o auth_request. Если модуль отсутствует, потребуется пересобрать Nginx с флагом --with-http_auth_request_module. Базовая структура конфигурации для любого защищаемого сервиса включает блок location = /api/auth для проксирования запросов к Authelia и директиву auth_request в основном блоке location /.
Критически важные директивы:
auth_request /api/auth;– включает проверку авторизации для данного location.auth_request_set $user $upstream_http_remote_user;– извлекает имя пользователя из заголовка ответа Authelia.proxy_set_header X-Forwarded-User $user;– передает имя пользователя в защищаемое приложение.error_page 401 =302 https://auth.your-domain.com/?rd=$scheme://$host$request_uri;– перенаправляет неавторизованных пользователей на страницу входа Authelia.
Конфигурация для защиты панели TrueNAS Scale/Core
Предполагается, что TrueNAS доступен внутри сети по адресу http://192.168.1.10 (или по HTTPS на порту 443). Nginx будет слушать публичный порт 443 с SSL для домена nas.your-domain.com.
server {
listen 443 ssl http2;
server_name nas.your-domain.com;
# Ваши настройки SSL (сертификат, протоколы, шифры)
ssl_certificate /etc/ssl/certs/nas.your-domain.com.fullchain.pem;
ssl_certificate_key /etc/ssl/private/nas.your-domain.com.key;
# Рекомендуемые настройки из руководства по безопасности
include /etc/nginx/snippets/ssl-params.conf;
# Внутренний endpoint для проверки авторизации Authelia
location = /api/auth {
internal;
proxy_pass http://authelia:9091/api/verify; # Используем имя сервиса из Docker сети
proxy_pass_request_body off;
proxy_set_header Content-Length "";
proxy_set_header X-Original-URL $scheme://$http_host$request_uri;
proxy_set_header X-Forwarded-Method $request_method;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-Host $http_host;
proxy_set_header X-Forwarded-Uri $request_uri;
proxy_set_header X-Forwarded-For $remote_addr;
}
location / {
# Проверка аутентификации через Authelia
auth_request /api/auth;
auth_request_set $user $upstream_http_remote_user;
auth_request_set $groups $upstream_http_remote_groups;
auth_request_set $name $upstream_http_remote_name;
auth_request_set $email $upstream_http_remote_email;
# Передача данных пользователя в TrueNAS (если нужно)
proxy_set_header X-Forwarded-User $user;
# Проксирование на TrueNAS
proxy_pass http://192.168.1.10;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
# Важно для работы WebSocket в TrueNAS Scale
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_read_timeout 86400;
# Обработка ошибки 401 - редирект на логин
error_page 401 =302 https://auth.your-domain.com/?rd=$scheme://$host$request_uri;
}
}
После применения конфигурации (nginx -t && systemctl reload nginx) при попытке доступа к https://nas.your-domain.com вас сначала перенаправит на страницу входа Authelia с запросом TOTP-кода.
Конфигурация для защиты панели Proxmox VE
Конфигурация для Proxmox имеет особенности из-за использования им самоподписанных сертификатов и отдельных портов для веб-интерфейса (8006) и API. Важно корректно проксировать оба endpoint и отключить проверку SSL при проксировании на локальный PVE, чтобы избежать ошибок из-за самоподписанных сертификатов.
server {
listen 443 ssl http2;
server_name pve.your-domain.com;
# Настройки SSL
ssl_certificate /etc/ssl/certs/pve.your-domain.com.fullchain.pem;
ssl_certificate_key /etc/ssl/private/pve.your-domain.com.key;
include /etc/nginx/snippets/ssl-params.conf;
location = /api/auth {
internal;
proxy_pass http://authelia:9091/api/verify;
proxy_pass_request_body off;
proxy_set_header Content-Length "";
proxy_set_header X-Original-URL $scheme://$http_host$request_uri;
proxy_set_header X-Forwarded-Method $request_method;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-Host $http_host;
proxy_set_header X-Forwarded-Uri $request_uri;
proxy_set_header X-Forwarded-For $remote_addr;
}
location / {
auth_request /api/auth;
auth_request_set $user $upstream_http_remote_user;
proxy_set_header X-Forwarded-User $user;
# Проксирование на веб-интерфейс Proxmox (порт 8006)
proxy_pass https://192.168.1.20:8006;
proxy_ssl_verify off; # Игнорируем самоподписанный сертификат PVE
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
# Увеличенные таймауты для длительных операций (миграция, бэкап)
proxy_connect_timeout 300;
proxy_send_timeout 300;
proxy_read_timeout 300;
error_page 401 =302 https://auth.your-domain.com/?rd=$scheme://$host$request_uri;
}
# Отдельный location для API Proxmox, если требуется
location /api2/json/ {
auth_request /api/auth;
proxy_pass https://192.168.1.20:8007/api2/json/;
proxy_ssl_verify off;
proxy_set_header Host $host;
# ... остальные proxy_set_header
}
}
Эта конфигурация обеспечивает прозрачную работу Proxmox VE через Nginx с обязательной двухфакторной аутентификацией. Для тонкой настройки сетевого доступа к файловым ресурсам, которые могут быть связаны с виртуальными машинами, полезно ознакомиться с руководством по настройке SMB, NFS и FTP в TrueNAS.
Тестирование, отладка и решение частых проблем
После настройки выполните пошаговый чек-лист:
- Доступность Authelia:
curl -k https://auth.your-domain.com/api/health. - Прямой доступ к панели по внутреннему IP (например,
https://192.168.1.10), чтобы убедиться, что она работает. - Попытка доступа по публичному домену. Должен произойти редирект на страницу входа Authelia.
- Успешный вход с логином, паролем и TOTP-кодом.
- После входа – доступ к интерфейсу TrueNAS/Proxmox.
Основные источники диагностики – логи Nginx (/var/log/nginx/error.log) и логи контейнера Authelia (docker logs authelia). Распространенные ошибки:
- 502 Bad Gateway: Nginx не может соединиться с Authelia. Проверьте сетевую доступность, правильность имени хоста/порта в
proxy_pass, работает ли контейнер Authelia. - 401/403 после ввода креденшиалов: Ошибка конфигурации Authelia. Проверьте файл
users_database.yml, правильность хэша пароля, соответствие домена в правилеaccess_control. - Зацикливание редиректов: Неверно настроен
error_page 401или URL редиректа в Authelia (default_redirection_url). Убедитесь, что домены в конфигах Nginx и Authelia совпадают.
Для глубокой диагностики ошибок авторизации, которые могут возникать в сложных средах с Docker и Kubernetes, используйте методы из руководства по диагностике ошибок 401 и 403.
Как обеспечить отказоустойчивость и что делать при падении Authelia
Сервис централизованной аутентификации становится критическим звеном. Его отказ не должен блокировать доступ ко всей инфраструктуре. Реализуйте стратегию высокой доступности:
- Репликация состояния: Настройте несколько инстансов Authelia с общей базой данных (PostgreSQL) и хранилищем сессий (Redis).
- Балансировка нагрузки: Разместите инстансы Authelia за внутренним балансировщиком (HAProxy, другой Nginx) и укажите его адрес в директиве
proxy_passNginx. - Механизм обнаружения сбоев (Dead Server Detection): Настройте в блоке
location /api/authдирективы для обработки таймаутов и сбоев бэкенда:
Это аналогично принципу AAA Dead Server Detection в сетевом оборудовании Cisco, где неотвечающий RADIUS-сервер временно исключается из пула.proxy_next_upstream error timeout invalid_header http_500 http_502 http_503 http_504; proxy_connect_timeout 2s; proxy_read_timeout 5s;
План аварийного восстановления должен включать возможность временного отключения проверки auth_request. Создайте резервную конфигурацию Nginx без блока location = /api/auth и директивы auth_request в основном location. В критической ситуации замените конфиг и перезагрузите Nginx. Это восстановит доступ по базовой аутентификации TrueNAS/Proxmox, но позволит продолжить работу. После восстановления Authelia верните исходную конфигурацию. Для комплексной защиты сервера, на котором развернуты эти сервисы, применяйте методы из практического руководства по харденингу Linux-сервера.
Дальнейшие шаги: мониторинг, аудит и расширение защиты
После успешного развертывания системы централизованной 2FA сосредоточьтесь на мониторинге и развитии инфраструктуры безопасности.
- Мониторинг и аудит: Настройте сбор логов Authelia в централизованную систему (ELK Stack, Grafana Loki). Отслеживайте успешные и неудачные попытки входа, особенно с большим количеством попыток (
max_retries). Настройте уведомления в Telegram или по email о подозрительной активности (множественные 401 ошибки с одного IP). - Расширение защиты: Примените ту же схему с Nginx
auth_requestи Authelia для защиты других внутренних веб-сервисов: Nextcloud, GitLab, Grafana, Portainer. Это создаст единое защищенное пространство доступа (Zero Trust Network). - Интеграция с корпоративной инфраструктурой: Если в вашей организации используется Active Directory или OpenLDAP, настройте в Authelia бэкенд
ldapвместоfile. Это позволит управлять пользователями и группами из центрального каталога. - Управление жизненным циклом: Регулярно обновляйте контейнеры Authelia и Nginx для получения исправлений уязвимостей. Используйте инструменты вроде Watchtower или Renovate для автоматизации. Храните секретные ключи (
jwt_secret,session.secret) в менеджере паролей или secrets-хранилище (HashiCorp Vault).
Это решение превращает Nginx в универсальный шлюз безопасности, а Authelia – в центр управления доступом. Такой подход не только закрывает брешь в виде отсутствия 2FA в популярных панелях управления, но и закладывает основу для более сложных политик контроля доступа и аудита в будущем. Для автоматизации развертывания и управления подобными сервисами рассмотрите использование контейнерных решений, подробно описанных в руководстве по развертыванию LEMP-стека. Если в вашем рабочем процессе активно используются нейросетевые модели для анализа кода или документации, сервис AiTunnel может упростить доступ к их API, предоставляя единую точку входа для GPT, Gemini и других моделей с оплатой в рублях.