Загрузка...
Загрузка...
Полное руководство по .htaccess для Apache. Редиректы, rewrite правила, безопасность, кэширование, сжатие. Практические примеры для веб-разработчиков и SEO.
Полный справочник правил редиректов в .htaccess: 301/302, regex-редиректы, смена домена, HTTPS, trailing slash. Готовые примеры для Apache.
БезопасностьПравила безопасности в .htaccess: блокировка ботов, защита от хотлинкинга, ограничение доступа, защита чувствительных файлов, rate limiting.
Веб-разработкаПолное руководство по настройке Nginx. Виртуальные хосты, SSL, проксирование, кэширование, безопасность. Практические примеры конфигов для разных проектов.
SEOПодробное руководство по работе с редиректами: типы, настройка, влияние на SEO. Практические примеры для веб-разработчиков и SEO-специалистов. Лучшие практики и типичные ошибки.
Поделитесь с коллегами или изучите другие материалы блога
Файл .htaccess — один из самых мощных и одновременно опасных инструментов в арсенале веб-разработчика. Одна строчка может перенаправить весь трафик на HTTPS, а другая — положить сайт с ошибкой 500. В этом руководстве мы разберём ключевые сценарии использования .htaccess: редиректы, rewrite-правила, безопасность, кэширование и производительность. Каждый раздел содержит готовые примеры кода, которые можно адаптировать под ваш проект.
.htaccess (Hypertext Access) — конфигурационный файл веб-сервера Apache, который управляет поведением сервера на уровне директории. В отличие от httpd.conf, .htaccess не требует перезагрузки сервера — изменения вступают в силу мгновенно.
При получении HTTP-запроса Apache проходит по цепочке директорий от корня до запрошенного файла и на каждом уровне проверяет наличие .htaccess. Директивы применяются последовательно, причём более глубокий файл перекрывает настройки родительского. Например, при запросе /blog/2026/article.html будут проверены /.htaccess, /blog/.htaccess и /blog/2026/.htaccess.
Базовая структура файла:
RewriteEngine On
AddDefaultCharset UTF-8
Options -Indexes
Чтобы Apache обрабатывал .htaccess, в основной конфигурации сервера должна быть директива AllowOverride:
<Directory /var/www/html>
AllowOverride All
Require all granted
</Directory>
Значение All разрешает все типы директив. Для повышения безопасности можно ограничить набор — AuthConfig (авторизация), FileInfo (редиректы, rewrite), Indexes (листинг директорий), Limit (ограничение доступа), Options (опции директорий).
Каждый .htaccess создаёт нагрузку: Apache читает и парсит файл при каждом запросе. На высоконагруженных проектах рекомендуется переносить директивы в httpd.conf. Но на shared-хостинге .htaccess остаётся единственным способом конфигурации. Быстро сгенерировать корректный файл поможет Генератор .htaccess на reChecker.
Редиректы — самая распространённая задача для .htaccess. Правильная настройка перенаправлений критически важна для SEO: она сохраняет ссылочный вес страниц и обеспечивает бесшовный переход пользователей.
# 301 — постоянный редирект (передаёт до 99% ссылочного веса)
Redirect 301 /old-page.html https://example.com/new-page.html
# То же через mod_rewrite
RewriteEngine On
RewriteRule ^old-page\.html$ /new-page.html [R=301,L]
# 302 — временный редирект (вес не передаётся)
Redirect 302 /promo /temporary-promo
Две версии сайта — это дублирование контента. Выберите каноническую версию:
# С www на без www
RewriteEngine On
RewriteCond %{HTTP_HOST} ^www\.example\.com$ [NC]
RewriteRule ^(.*)$ https://example.com/$1 [R=301,L]
# С без www на www
RewriteEngine On
RewriteCond %{HTTP_HOST} ^example\.com$ [NC]
RewriteRule ^(.*)$ https://www.example.com/$1 [R=301,L]
После установки SSL-сертификата необходимо перенаправить весь HTTP-трафик. Проверить корректность SSL можно через SSL Checker.
RewriteEngine On
RewriteCond %{HTTPS} off
RewriteRule ^(.*)$ https://%{HTTP_HOST}/$1 [R=301,L]
Для серверов за обратным прокси (CloudFlare, AWS ALB):
RewriteEngine On
RewriteCond %{HTTP:X-Forwarded-Proto} !https
RewriteRule ^(.*)$ https://%{HTTP_HOST}/$1 [R=301,L]
На практике часто нужно объединить несколько редиректов. Правильный подход — одно 301 перенаправление вместо цепочки:
RewriteEngine On
RewriteCond %{HTTPS} off [OR]
RewriteCond %{HTTP_HOST} ^www\. [NC]
RewriteCond %{HTTP_HOST} ^(?:www\.)?(.+)$ [NC]
RewriteRule ^(.*)$ https://%1/$1 [R=301,L]
Единообразие URL — важный SEO-фактор:
# Добавить trailing slash
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_URI} !(.*)/$
RewriteRule ^(.*)$ /$1/ [R=301,L]
# Убрать trailing slash
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_URI} (.+)/$
RewriteRule ^(.+)/$ /$1 [R=301,L]
RewriteEngine On
# Редирект раздела
RewriteRule ^blog/category/(.*)$ /articles/topic/$1 [R=301,L]
# Редирект с GET-параметрами
RewriteCond %{QUERY_STRING} ^id=(\d+)$
RewriteRule ^product\.php$ /catalog/product-%1.html? [R=301,L]
# Редирект на другой домен
RewriteRule ^(.*)$ https://newdomain.com/$1 [R=301,L]
Проверить корректность настроенных редиректов можно через инструмент проверки редиректов — он покажет всю цепочку перенаправлений и выявит циклы.
Перезапись URL создаёт человекочитаемые адреса вместо технических GET-параметров. Это положительно влияет на SEO и удобство пользователей.
RewriteRule шаблон подстановка [флаги]
Шаблон — регулярное выражение для URI (без ведущего /). Подстановка — новый URI. Основные флаги:
| Флаг | Описание |
|---|---|
[L] | Последнее правило — прекращает обработку |
[R=301] | Внешний редирект с кодом 301 |
[NC] | Регистронезависимое сравнение |
[QSA] | Добавить исходную строку запроса к новому URL |
[F] | Вернуть 403 Forbidden |
[G] | Вернуть 410 Gone |
[END] | Полностью завершить обработку (Apache 2.4+) |
RewriteCond %{HTTPS} on # Проверка HTTPS
RewriteCond %{REQUEST_METHOD} POST # Метод запроса
RewriteCond %{HTTP_USER_AGENT} "Googlebot" [NC] # User-Agent
RewriteCond %{REQUEST_FILENAME} !-f # Файл не существует
RewriteCond %{REQUEST_FILENAME} !-d # Директория не существует
RewriteCond %{QUERY_STRING} ^lang=([a-z]{2})$ # Строка запроса
ЧПУ для блога:
RewriteEngine On
RewriteRule ^blog/([a-z0-9\-]+)$ blog.php?slug=$1 [L,QSA]
RewriteRule ^blog/(\d{4})/(\d{2})/([a-z0-9\-]+)$ blog.php?year=$1&month=$2&slug=$3 [L,QSA]
ЧПУ для каталога:
RewriteEngine On
RewriteRule ^catalog/([a-z\-]+)/([a-z\-]+)$ catalog.php?category=$1&sub=$2 [L,QSA]
RewriteRule ^product/([a-z0-9\-]+)$ product.php?slug=$1 [L,QSA]
Мультиязычный сайт:
RewriteEngine On
RewriteRule ^(en|ru|de|fr)/(.+)$ page.php?lang=$1&page=$2 [L,QSA]
Приведение URL к нижнему регистру (Apache 2.4+):
RewriteMap lowercase int:tolower
RewriteCond %{REQUEST_URI} [A-Z]
RewriteRule ^(.*)$ ${lowercase:$1} [R=301,L]
.htaccess — первая линия обороны, работающая до того, как запрос дойдёт до приложения.
AuthType Basic
AuthName "Restricted Area"
AuthUserFile /home/user/.htpasswd
Require valid-user
Создание .htpasswd: htpasswd -c /home/user/.htpasswd admin
Защита конкретного файла:
<Files "admin.php">
AuthType Basic
AuthName "Admin Access"
AuthUserFile /home/user/.htpasswd
Require user admin
</Files>
# Apache 2.4 — заблокировать IP
<RequireAll>
Require all granted
Require not ip 192.168.1.100
Require not ip 10.0.0.0/8
</RequireAll>
# Доступ только с определённых IP
<RequireAny>
Require ip 203.0.113.50
Require ip 198.51.100.0/24
</RequireAny>
RewriteEngine On
RewriteCond %{HTTP_REFERER} !^$
RewriteCond %{HTTP_REFERER} !^https?://(www\.)?example\.com [NC]
RewriteCond %{HTTP_REFERER} !^https?://(www\.)?google\. [NC]
RewriteCond %{HTTP_REFERER} !^https?://(www\.)?yandex\. [NC]
RewriteRule \.(jpg|jpeg|png|gif|webp|svg)$ - [F,NC]
Для аудита текущих заголовков используйте проверку заголовков безопасности.
<IfModule mod_headers.c>
Header set X-Content-Type-Options "nosniff"
Header set X-XSS-Protection "1; mode=block"
Header set X-Frame-Options "SAMEORIGIN"
Header set Strict-Transport-Security "max-age=31536000; includeSubDomains; preload"
Header set Referrer-Policy "strict-origin-when-cross-origin"
Header set Permissions-Policy "camera=(), microphone=(), geolocation=(self)"
Header set 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' https://fonts.gstatic.com"
</IfModule>
RewriteEngine On
RewriteCond %{HTTP_USER_AGENT} (SemrushBot|AhrefsBot|MJ12bot|DotBot) [NC]
RewriteRule .* - [F,L]
RewriteCond %{HTTP_USER_AGENT} ^$
RewriteRule .* - [F,L]
<LimitExcept GET POST HEAD>
Require all denied
</LimitExcept>
Кэширование снижает нагрузку на сервер и ускоряет загрузку для повторных посетителей.
<IfModule mod_expires.c>
ExpiresActive On
ExpiresDefault "access plus 1 month"
ExpiresByType text/html "access plus 0 seconds"
ExpiresByType text/css "access plus 1 year"
ExpiresByType application/javascript "access plus 1 year"
ExpiresByType image/jpeg "access plus 1 year"
ExpiresByType image/png "access plus 1 year"
ExpiresByType image/webp "access plus 1 year"
ExpiresByType image/svg+xml "access plus 1 year"
ExpiresByType image/x-icon "access plus 1 year"
ExpiresByType font/woff2 "access plus 1 year"
ExpiresByType font/woff "access plus 1 year"
ExpiresByType application/json "access plus 0 seconds"
</IfModule>
Cache-Control даёт более гибкое управление:
<IfModule mod_headers.c>
<FilesMatch "\.(html|htm)$">
Header set Cache-Control "no-cache, no-store, must-revalidate"
</FilesMatch>
<FilesMatch "\.(css|js)$">
Header set Cache-Control "public, max-age=31536000, immutable"
</FilesMatch>
<FilesMatch "\.(jpg|jpeg|png|gif|webp|svg|ico)$">
Header set Cache-Control "public, max-age=31536000, immutable"
</FilesMatch>
<FilesMatch "\.(woff2|woff|ttf|eot)$">
Header set Cache-Control "public, max-age=31536000, immutable"
</FilesMatch>
</IfModule>
На кластерных серверах ETag может вызывать проблемы — его лучше отключить:
Header unset ETag
FileETag None
Сжатие уменьшает размер передаваемых данных на 60-80%.
<IfModule mod_deflate.c>
AddOutputFilterByType DEFLATE text/html text/css text/javascript text/xml text/plain
AddOutputFilterByType DEFLATE application/javascript application/json
AddOutputFilterByType DEFLATE application/xml application/rss+xml application/xhtml+xml
AddOutputFilterByType DEFLATE image/svg+xml
AddOutputFilterByType DEFLATE font/woff font/woff2 application/vnd.ms-fontobject
SetEnvIfNoCase Request_URI \.(?:gif|jpe?g|png|webp|zip|gz|bz2|rar|mp[34])$ no-gzip
BrowserMatch ^Mozilla/4 gzip-only-text/html
BrowserMatch ^Mozilla/4\.0[678] no-gzip
BrowserMatch \bMSIE !no-gzip !gzip-only-text/html
Header append Vary Accept-Encoding
</IfModule>
curl -H "Accept-Encoding: gzip" -I https://example.com/style.css
В ответе должен быть заголовок Content-Encoding: gzip.
Стандартные страницы Apache выглядят непрофессионально и раскрывают информацию о сервере.
ErrorDocument 400 /errors/400.html
ErrorDocument 401 /errors/401.html
ErrorDocument 403 /errors/403.html
ErrorDocument 404 /errors/404.html
ErrorDocument 500 /errors/500.html
ErrorDocument 503 /errors/503.html
Не используйте ErrorDocument 404 https://example.com/not-found — внешний редирект вернёт код 302, а не 404, что навредит SEO.
RewriteEngine On
RewriteCond %{REMOTE_ADDR} !^203\.0\.113\.50$
RewriteCond %{REQUEST_URI} !\.(css|js|png|jpg|gif|ico|svg|woff2?)$ [NC]
RewriteCond %{REQUEST_URI} !^/maintenance\.html$
RewriteRule ^(.*)$ /maintenance.html [R=503,L]
Header set Retry-After "3600"
IP разработчика пропускается, статические ресурсы загружаются, а поисковые системы получают заголовок Retry-After и понимают, что ситуация временная.
Утечка конфигурационных файлов — одна из распространённых причин взлома.
<FilesMatch "^\.">
Require all denied
</FilesMatch>
<FilesMatch "(\.env|\.env\..*|\.htpasswd)$">
Require all denied
</FilesMatch>
WordPress — закрываем wp-config.php и xmlrpc.php (частая цель brute-force атак):
<Files wp-config.php>
Require all denied
</Files>
<Files xmlrpc.php>
Require all denied
</Files>
Bitrix:
<Files ".settings.php">
Require all denied
</Files>
<Files "dbconn.php">
Require all denied
</Files>
RedirectMatch 404 /\.git
<FilesMatch "\.(sql|sql\.gz|bak|backup|old|orig|save|swp|log|ini|conf|cfg)$">
Require all denied
</FilesMatch>
<FilesMatch "^(config|database|functions|helpers|bootstrap)\.php$">
Require all denied
</FilesMatch>
Собрать все правила защиты в единый конфигурационный файл поможет генератор .htaccess на reChecker — он создаст готовую конфигурацию с учётом вашего стека.
<IfModule mod_headers.c>
Header set Connection keep-alive
<FilesMatch "\.(woff2?|ttf|eot|otf)$">
Header set Access-Control-Allow-Origin "*"
</FilesMatch>
</IfModule>
<IfModule mod_mime.c>
AddType image/webp .webp
AddType image/avif .avif
AddType font/woff2 .woff2
AddType font/woff .woff
AddType application/manifest+json .webmanifest
AddType video/mp4 .mp4
AddType video/webm .webm
AddType text/javascript .mjs
</IfModule>
<Directory "/var/www/html/uploads">
RemoveHandler .php
<FilesMatch "\.(php|phtml|php[3-7]|phps|phar|cgi|pl|py|sh)$">
Require all denied
</FilesMatch>
</Directory>
Самая частая проблема. Основные причины:
# 1. Синтаксическая ошибка
Rewrite Engine On # НЕПРАВИЛЬНО — лишний пробел
RewriteEngine On # ПРАВИЛЬНО
# 2. Модуль не установлен — используйте обёртку
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteRule ^old$ /new [R=301,L]
</IfModule>
# 3. Относительный путь к .htpasswd
AuthUserFile .htpasswd # НЕПРАВИЛЬНО
AuthUserFile /home/username/.htpasswd # ПРАВИЛЬНО
# Проблема — правило перенаправляет URL на себя
RewriteRule ^(.*)$ /index.php [L]
# Решение — исключаем существующие файлы
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ /index.php [L]
Частые причины: отключён AllowOverride, отсутствует RewriteEngine On (не наследуется от родительских файлов), неправильный порядок правил:
RewriteEngine On
# НЕПРАВИЛЬНО — общее правило перехватывает всё
RewriteRule ^(.*)$ /index.php [L]
RewriteRule ^api/(.*)$ /api/handler.php?route=$1 [L]
# ПРАВИЛЬНО — частные правила первыми
RewriteRule ^api/(.*)$ /api/handler.php?route=$1 [L]
RewriteRule ^(.*)$ /index.php [L]
Если сайт в подкаталоге (example.com/myapp/), без RewriteBase правила работают некорректно:
RewriteEngine On
RewriteBase /myapp/
RewriteRule ^page/(\d+)$ index.php?page=$1 [L]
apachectl configtest # Проверка синтаксиса
tail -f /var/log/apache2/error.log # Лог ошибок
Для детальной отладки rewrite-правил (в httpd.conf, не в .htaccess):
LogLevel alert rewrite:trace3
.htaccess остаётся незаменимым инструментом настройки Apache, особенно на shared-хостингах. Ключевые рекомендации:
.htaccess перед изменениями. Одна опечатка — и сайт вернёт 500.<IfModule> для предотвращения ошибок при отсутствии модулей..htaccess на высоконагруженных проектах — переносите правила в конфигурацию виртуального хоста.Хорошо настроенный .htaccess — это одновременно защита, производительность и корректная работа SEO. Потратьте время на его настройку один раз, и ваш сервер будет работать надёжнее, быстрее и безопаснее.