HTTP Security Headers: полный гид по CSP, HSTS, X-Frame-Options
Зачем нужны HTTP-заголовки безопасности
HTTP-заголовки безопасности — это инструкции, которые сервер отправляет браузеру вместе с веб-страницей. Они указывают браузеру, как обрабатывать контент, какие ресурсы загружать и какие функции отключить.
Правильно настроенные заголовки:
- Защищают от XSS — предотвращают выполнение вредоносных скриптов
- Предотвращают clickjacking — запрещают встраивание сайта в iframe
- Обеспечивают HTTPS — принудительное шифрование
- Контролируют ресурсы — ограничивают загрузку сторонних скриптов
- Защищают приватность — контролируют утечку информации через referrer
Большинство сайтов не настраивают все основные заголовки безопасности корректно.
Content-Security-Policy (CSP)
Что делает
CSP — самый мощный заголовок безопасности. Определяет, откуда браузер может загружать ресурсы: скрипты, стили, изображения, шрифты, фреймы.
Почему критически важен
CSP — главная защита от XSS-атак. Даже если злоумышленник внедрит скрипт, CSP не позволит его выполнить, если источник не в белом списке.
Основные директивы
Content-Security-Policy:
default-src 'self';
script-src 'self' https://cdn.example.com;
style-src 'self' 'unsafe-inline';
img-src 'self' data: https:;
font-src 'self';
connect-src 'self' https://api.example.com;
frame-ancestors 'none';
base-uri 'self';
form-action 'self'
default-src 'self'— по умолчанию только со своего доменаscript-src 'self' https://cdn.example.com— скрипты со своего домена и CDNstyle-src 'self' 'unsafe-inline'— стили со своего домена и inlineimg-src 'self' data: https:— изображения со своего домена и любые HTTPSframe-ancestors 'none'— запрет встраивания в iframebase-uri 'self'— защита от base tag injectionform-action 'self'— формы отправляются только на свой домен
Пошаговое внедрение
Шаг 1: Report-Only — начните с Content-Security-Policy-Report-Only, который не блокирует, а логирует нарушения.
Шаг 2: Анализ отчётов — соберите данные о загружаемых ресурсах.
Шаг 3: Enforcement — переключитесь на блокирующий режим.
Типичные ошибки
unsafe-inlineвscript-src— обнуляет защиту от XSSunsafe-eval— позволяет выполнять строки как код- Слишком широкие источники (
*,https:) — ослабляют политику - Отсутствие
default-src— ресурсы без директивы не ограничены
Настройка nginx
add_header Content-Security-Policy "default-src 'self'; script-src 'self'; style-src 'self' 'unsafe-inline'; img-src 'self' data: https:; frame-ancestors 'none'" always;
Настройка Apache
Header always set Content-Security-Policy "default-src 'self'; frame-ancestors 'none'"
Strict-Transport-Security (HSTS)
Что делает
HSTS указывает браузеру всегда использовать HTTPS. После получения заголовка браузер автоматически перенаправляет HTTP на HTTPS.
Почему важен
Защищает от:
- SSL Stripping — перехват первого HTTP-запроса
- Случайного перехода на HTTP — клик на старую ссылку
- Mixed Content — загрузка HTTP-ресурсов на HTTPS-странице
Рекомендуемая конфигурация
Strict-Transport-Security: max-age=31536000; includeSubDomains; preload
max-age=31536000— запомнить на 1 годincludeSubDomains— распространить на поддоменыpreload— заявка на HSTS Preload List
HSTS Preload List
Браузеры Chrome, Firefox, Safari и Edge поддерживают Preload List — HSTS работает ещё до первого посещения. Подать заявку: hstspreload.org
Настройка nginx
add_header Strict-Transport-Security "max-age=31536000; includeSubDomains; preload" always;
X-Frame-Options
Что делает
Управляет встраиванием страницы в <iframe>, <frame>, <embed>, <object>.
Почему важен
Защищает от clickjacking — ваш сайт в невидимом iframe, пользователь нажимает на кнопки, не видя их.
Значения
DENY— полный запретSAMEORIGIN— только со своего домена
X-Frame-Options: DENY
Примечание: CSP frame-ancestors — современная замена. Используйте оба для совместимости.
X-Content-Type-Options
Что делает
Запрещает MIME sniffing — браузер использует только тип, указанный сервером.
Почему важен
Без него браузер может интерпретировать файл как скрипт. Это путь для XSS через загрузку файлов.
X-Content-Type-Options: nosniff
Referrer-Policy
Что делает
Контролирует информацию о URL при переходе на другой сайт.
Почему важен
URL могут содержать токены сброса пароля, session ID, внутренние пути. Без контроля они утекают к сторонним сайтам.
Рекомендуемые значения
strict-origin-when-cross-origin— при переходе на другой сайт только origin, внутри сайта — полный URLno-referrer— никогда не передаватьsame-origin— только внутри сайта
Referrer-Policy: strict-origin-when-cross-origin
Permissions-Policy
Что делает
Контролирует API браузера: камера, микрофон, геолокация, платежи.
Почему важен
Ограничивает доступ к чувствительным API от сторонних скриптов и iframe.
Permissions-Policy: camera=(), microphone=(), geolocation=(), payment=(), usb=()
Пустые скобки () означают полный запрет.
Полная конфигурация nginx
server {
add_header Strict-Transport-Security "max-age=31536000; includeSubDomains; preload" always;
add_header Content-Security-Policy "default-src 'self'; script-src 'self'; style-src 'self' 'unsafe-inline'; img-src 'self' data: https:; frame-ancestors 'none'; base-uri 'self'" always;
add_header X-Frame-Options "DENY" always;
add_header X-Content-Type-Options "nosniff" always;
add_header Referrer-Policy "strict-origin-when-cross-origin" always;
add_header Permissions-Policy "camera=(), microphone=(), geolocation=(), payment=()" always;
}
Полная конфигурация Apache
<IfModule mod_headers.c>
Header always set Strict-Transport-Security "max-age=31536000; includeSubDomains; preload"
Header always set Content-Security-Policy "default-src 'self'; frame-ancestors 'none'"
Header always set X-Frame-Options "DENY"
Header always set X-Content-Type-Options "nosniff"
Header always set Referrer-Policy "strict-origin-when-cross-origin"
Header always set Permissions-Policy "camera=(), microphone=(), geolocation=()"
</IfModule>
Проверка заголовков
После настройки проверьте результат:
- DevTools — вкладка Network, Response Headers
- curl —
curl -I https://example.com - Онлайн — Проверка заголовков Периметра покажет наличие всех заголовков и оценит конфигурацию
Частые ошибки
1. Заголовки только для HTML
Настройте заголовки глобально (always в nginx), включая API-ответы.
2. Конфликт location-блоков
В nginx заголовки в location переопределяют server. Дублируйте заголовки в каждом location.
3. CSP ломает функциональность
Начинайте с Report-Only, тестируйте на staging.
4. Слишком мягкие политики
CSP с unsafe-inline unsafe-eval * бесполезен. Начните строго и ослабляйте по необходимости.
Что настроить в первую очередь
HTTP-заголовки безопасности — простая и эффективная мера защиты. Настройка занимает минуты, защита работает для всех пользователей.
Минимальный набор:
- HSTS — принудительный HTTPS
- CSP — защита от XSS
- X-Frame-Options — защита от clickjacking
- X-Content-Type-Options — защита от MIME sniffing
- Referrer-Policy — контроль утечки URL
Проверьте заголовки вашего сайта: perimeter-scan.ru/tools/headers-check
Похожие статьи
Полное руководство по настройке SPF, DKIM и DMARC для защиты email
Пошаговое руководство по настройке SPF, DKIM и DMARC: примеры DNS-записей, типичные ошибки, проверка и дополнительные протоколы BIMI и MTA-STS.
Как проверить безопасность своего сайта: пошаговый чек-лист 2026 года
Полный чек-лист из 20 пунктов для проверки безопасности сайта: SSL, заголовки, DNS, email-аутентификация, порты, утечки, WAF и OWASP.
