Выберите продукт

HTTP Basic Auth и белые списки: быстро закрываем сайт паролем в Nginx/Apache

Нужно быстро закрыть сайт от посторонних на предпросмотре, стейджинге или во время миграции? Используйте HTTP Basic Auth и белые списки IP. Показываю настройку пароля в Nginx и Apache (.htaccess), генерацию htpasswd, обход по allowlist и отладку.
HTTP Basic Auth и белые списки: быстро закрываем сайт паролем в Nginx/Apache

Если нужно временно спрятать сайт от посторонних без сложных систем доступа, самый быстрый способ — включить HTTP Basic Auth (защита паролем на уровне веб-сервера) и при необходимости добавить белый список IP-адресов (allowlist), чтобы своей команде не вводить пароль каждый раз. Дальше — практический разбор для Nginx и Apache, с рабочими сниппетами, нюансами и отладкой.

Зачем закрывать сайт паролем именно на уровне веб-сервера

HTTP Basic Auth работает до приложения, поэтому:

  • не допускает индексации поисковиками (получают 401 и не идут дальше),
  • не требует прав на код, CMS или фреймворк,
  • быстро включается и выключается одной правкой конфигурации,
  • моментально покрывает весь сайт или выбранные разделы.

Типовые сценарии: предпросмотр нового проекта, закрытый стейджинг, миграция или редизайн, защита панели администрирования, приватные файловые каталоги, внутренние демо. Для миграций полезен чек-лист по доменам, редиректам и HSTS — см. разбор миграции доменов, редиректов и HSTS.

Важно: Basic Auth не шифрует трафик — логин и пароль передаются в заголовке Authorization в Base64. Обязательно используйте HTTPS и установите SSL-сертификаты, чтобы не отдавать креды в открытом виде.

Кратко о механике HTTP Basic Auth

Сервер возвращает 401 Unauthorized и заголовок WWW-Authenticate: Basic realm="...". Браузер показывает диалог, а затем добавляет Authorization: Basic ... к каждому запросу. Realm — это подпись зоны, задаётся в конфиге и влияет на кэширование логина браузером.

Схема работы HTTP Basic Auth: запрос, 401, заголовки и ввод пароля

Готовим файл паролей: htpasswd

Оба сервера (и Nginx, и Apache) понимают формат пароля из файла .htpasswd. Лучше хранить его вне docroot, например в /etc/nginx/.htpasswd или /etc/apache2/.htpasswd. Права: достаточно чтения веб-сервером, другим пользователям — закрыть.

Установка утилиты и генерация

# Debian/Ubuntu
sudo apt-get update
sudo apt-get install apache2-utils

# RHEL/CentOS/Alma/Rocky
sudo dnf install httpd-tools

# Создать файл и первого пользователя (формат Apache MD5 APR1, совместим с Nginx)
sudo htpasswd -c -m /etc/nginx/.htpasswd admin

# Добавить ещё одного пользователя
sudo htpasswd -m /etc/nginx/.htpasswd dev

Ключи:

  • -c — создать новый файл (используйте только один раз, чтобы не перетереть существующих пользователей),
  • -m — хэш Apache MD5 APR1. Его понимает и Nginx, и Apache, поэтому это безопасный кросс-серверный выбор.

Для Apache можно использовать bcrypt (htpasswd -B), но Nginx на многих системах его не валидирует. Для совместимости выбираем -m или, при необходимости, генерируем APR1 через OpenSSL.

# Генерация APR1 через OpenSSL
openssl passwd -apr1
# Вставьте полученную строку как хэш в файл формата user:hash

Проверьте права и владельца:

sudo chown root:www-data /etc/nginx/.htpasswd
sudo chmod 640 /etc/nginx/.htpasswd

Подставьте правильного системного пользователя группы веб-сервера: www-data, nginx или apache.

Nginx: быстро закрываем весь сайт паролем

Минимальный фрагмент в серверном блоке:

server {
    listen 80;
    server_name example.com;

    auth_basic "Restricted";
    auth_basic_user_file /etc/nginx/.htpasswd;

    root /var/www/example.com;
    index index.html index.php;
}

Перезагрузите конфиг и проверьте:

sudo nginx -t
sudo systemctl reload nginx

Только для выбранного раздела

location /admin/ {
    auth_basic "Admin Area";
    auth_basic_user_file /etc/nginx/.htpasswd;
}

Остальная часть сайта останется открытой.

Белый список IP с обходом пароля

Чтобы сотрудники с доверенных IP не видели окно пароля, используйте satisfy any: доступ разрешён, если выполнено хотя бы одно условие (IP в allowlist ИЛИ верная пара логин/пароль).

location / {
    satisfy any;

    allow 203.0.113.10;
    allow 2001:db8::/32;
    deny all;

    auth_basic "Restricted";
    auth_basic_user_file /etc/nginx/.htpasswd;
}

Порядок директив важен: сначала satisfy и allow/deny, затем auth_basic. Иначе можно получить неожиданный 401/403.

Nginx за обратным прокси/CDN

Если Nginx стоит за балансировщиком или CDN, реальный IP клиента может не совпадать с $remote_addr. Тогда allowlist работать не будет, пока не доверите источник и не поднимете реальный IP:

set_real_ip_from 192.0.2.0/24;
real_ip_header X-Forwarded-For;
real_ip_recursive on;

Укажите подсеть или адрес вашего прокси. Никогда не доверяйте всем подряд источникам X-Forwarded-For — это критично для безопасности.

FastFox VDS
Облачный VDS-сервер в России
Аренда виртуальных серверов с моментальным развертыванием инфраструктуры от 195₽ / мес

Исключения для статических файлов

Иногда ассеты должны быть доступны без пароля (например, публичный логотип). Можно снять Basic Auth на подмножестве:

location ~* \.(css|js|png|jpg|gif|woff2?)$ {
    auth_basic off;
}

Разумеется, делайте это осознанно: любые исключения — потенциальная поверхность утечки.

Apache 2.4: защита в виртуальном хосте или через .htaccess

В Apache можно включить Basic Auth в конфиге виртуального хоста или локально в .htaccess. Предпочтительнее — конфиг vhost: быстрее и прозрачнее. .htaccess выбирают, когда нет доступа к глобальному конфигу (это типично для виртуального хостинга). На собственном VDS удобнее править конфигурацию полностью.

Вариант 1: конфиг виртуального хоста

<Directory "/var/www/example.com">
    AuthType Basic
    AuthName "Restricted"
    AuthUserFile /etc/apache2/.htpasswd
    Require valid-user
</Directory>

Перезапуск:

sudo apachectl configtest
sudo systemctl reload apache2

Вариант 2: .htaccess

Содержимое /var/www/example.com/.htaccess:

AuthType Basic
AuthName "Restricted"
AuthUserFile /etc/apache2/.htpasswd
Require valid-user

Убедитесь, что в конфигурации разрешены директивы авторизации:

<Directory "/var/www/example.com">
    AllowOverride AuthConfig
</Directory>

Белый список IP и обход пароля

Современный способ (Apache 2.4): контейнер <RequireAny>. Доступ даётся, если выполнено хотя бы одно условие.

<Directory "/var/www/example.com">
    AuthType Basic
    AuthName "Restricted"
    AuthUserFile /etc/apache2/.htpasswd

    <RequireAny>
        Require ip 203.0.113.10
        Require ip 2001:db8::/32
        Require valid-user
    </RequireAny>
</Directory>

Для .htaccess синтаксис тот же — просто поместите блок <RequireAny> внутрь файла.

Старый синтаксис (Allow from, Deny from, Satisfy any) — часть модуля совместимости и не рекомендуется в новых конфигурациях.

Только для каталога /admin

<Directory "/var/www/example.com/admin">
    AuthType Basic
    AuthName "Admin Area"
    AuthUserFile /etc/apache2/.htpasswd
    Require valid-user
</Directory>

Прячем сам .htpasswd от прямого доступа

Храните файл за пределами docroot. Если по какой-то причине он лежит внутри, закройте паттерн на уровне сервера.

# Apache
<Files ".ht*">
    Require all denied
</Files>
# Nginx
location ~ /\.ht {
    deny all;
}

Отладка и проверка

Проверьте ответ кодом и заголовками:

curl -I https://example.com/
# Должно прийти: HTTP/1.1 401 Unauthorized и WWW-Authenticate
curl -I -u admin:secret https://example.com/
# Должно прийти: HTTP/1.1 200 OK

Проверьте обход по IP, сделав запрос из сети с доверенного адреса или через туннель. Если видите 403 вместо 401 — правило allow/deny отрабатывает до авторизации. Убедитесь, что включили satisfy any (Nginx) или <RequireAny> (Apache).

Проверка Basic Auth через curl и фрагменты конфигураций

Типичные ошибки и быстрые решения

  • Apache: .htaccess не работает. Часто причина — AllowOverride None. Разрешите AllowOverride AuthConfig или вынесите правила в vhost.
  • Неверный путь к AuthUserFile. Проверьте абсолютный путь, права доступа и владельца. Apache/Nginx должен уметь читать файл.
  • Nginx не принимает пароль, созданный htpasswd -B. Используйте -m (APR1) или генерируйте хэш через openssl passwd -apr1.
  • Allowlist за прокси не срабатывает. Поднимите реальный IP через set_real_ip_from и real_ip_header в Nginx, либо соответствующие модули в Apache, доверяя только вашим прокси.
  • Браузер «залипает» с кэшем логина. Измените AuthName/realm, чтобы форсировать новое окно авторизации, или закройте все вкладки/перезапустите браузер.
  • Случайная раздача .htpasswd. Держите файл вне docroot и запретите любые файлы, начинающиеся на .ht, через правила сервера.

Комбинации и расширения

  • Только HEAD/GET. Обычно Basic Auth применяется ко всем методам. Для API можно точечно ограничивать методы и локации отдельными блоками.
  • Множественные зоны. Для разных разделов задайте разные AuthName и разные файлы пользователей.
  • Исключение проверок для мониторингов. Добавьте их IP в allowlist, чтобы не получать ложные алерты.
  • CMS-админка. Накрывайте /wp-admin, /cms/, /backend/ отдельными правилами, но не забывайте, что некоторые AJAX-эндпоинты могут жить вне каталога — проверяйте логи и открывайте точечно при необходимости.

Коды ответов и влияние на SEO

При включенном Basic Auth не будет индексации: боты получают 401 и не читают контент. При снятии защиты индексация возобновится. В продакшене вместо пароля используйте полноценные механизмы авторизации приложения. Параллельно настройте базовые security headers — см. гайд по заголовкам безопасности.

FastFox SSL
Надежные SSL-сертификаты
Мы предлагаем широкий спектр SSL-сертификатов от GlobalSign по самым низким ценам. Поможем с покупкой и установкой SSL бесплатно!

Готовые шаблоны «скопируй-вставь»

Nginx: весь сайт под паролем + allowlist

server {
    listen 443 ssl;
    server_name example.com;

    satisfy any;
    allow 203.0.113.10;
    deny all;

    auth_basic "Restricted";
    auth_basic_user_file /etc/nginx/.htpasswd;

    root /var/www/example.com;
    index index.html index.php;
}

Apache: .htaccess с обходом по IP

AuthType Basic
AuthName "Restricted"
AuthUserFile /etc/apache2/.htpasswd

<RequireAny>
    Require ip 203.0.113.10
    Require valid-user
</RequireAny>

Итоги

HTTP Basic Auth — быстрый, универсальный и предсказуемый способ закрыть сайт или разделы на уровне веб-сервера. Для совместимости генерируйте .htpasswd с APR1/MD5, храните его вне docroot, а доверенным командам добавляйте allowlist по IP. Не забывайте про HTTPS, реальные IP за прокси и логи — и защита сработает без сюрпризов.

Поделиться статьей

Вам будет интересно

Debian/Ubuntu: как исправить Device is busy у Docker network, volume и namespace OpenAI Статья написана AI (GPT 5)

Debian/Ubuntu: как исправить Device is busy у Docker network, volume и namespace

Если Docker на Debian или Ubuntu отвечает Device is busy при удалении сети, тома или namespace, причина обычно в живом процессе, о ...
Debian/Ubuntu: как исправить Host key verification failed в Ansible при смене IP OpenAI Статья написана AI (GPT 5)

Debian/Ubuntu: как исправить Host key verification failed в Ansible при смене IP

Ошибка Host key verification failed в Ansible на Debian и Ubuntu обычно возникает после переустановки сервера, смены IP или повтор ...
Debian/Ubuntu: duplicate address detected, DAD failed IPv6 — причины и исправление OpenAI Статья написана AI (GPT 5)

Debian/Ubuntu: duplicate address detected, DAD failed IPv6 — причины и исправление

Сообщения duplicate address detected и DAD failed в Debian/Ubuntu означают, что IPv6-адрес не прошёл проверку уникальности в локал ...