Когда не следует использовать mod_rewrite
Этот документ дополняет mod_rewrite документацию по справке. В нём описывается, пожалуй, один из самых важных концепций относительно mod_rewrite — а именно, когда следует избегать его использования.
mod_rewrite следует рассматривать как крайнюю меру, когда другие альтернативы оказываются недостаточными. Использование его при наличии более простых альтернатив приводит к конфигурациям, которые запутанны, ненадёжны и сложны в обслуживании. Понимание доступных альтернатив является очень важным шагом к овладению mod_rewrite.
Обратите внимание, что многие из этих примеров не будут работать без изменений в вашей конкретной конфигурации сервера, поэтому важно их понять, а не просто скопировать и вставить примеры в свою конфигурацию.
Наиболее распространённый случай, в котором mod_rewrite является подходящим инструментом, — это когда наилучшее решение требует доступа к файлам конфигурации сервера, и у вас нет такого доступа. Некоторые директивы конфигурации доступны только в файле конфигурации сервера. Поэтому, если вы находитесь в ситуации хостинга, где у вас есть только файлы .htaccess, вам может потребоваться прибегнуть к mod_rewrite.
Простое перенаправление
mod_alias предоставляет директивы Redirect и RedirectMatch, которые обеспечивают возможность перенаправления одного URL на другой. Такого рода простое перенаправление одного URL или класса URL-адресов куда-то ещё должно выполняться с помощью этих директив, а не RewriteRule. RedirectMatch позволяет вам включать регулярное выражение в критерии перенаправления, предоставляя многие преимущества использования RewriteRule.
Распространённое применение RewriteRule — перенаправление целого класса URL-адресов. Например, все URL-адреса в каталоге /one должны быть перенаправлены на http://one.example.com/, или, возможно, все запросы http должны быть перенаправлены на https.
Эти ситуации лучше обрабатываются директивой Redirect. Помните, что Redirect сохраняет информацию о пути. То есть перенаправление для URL /one также перенаправит все URL под ним, такие как /one/two.html и /one/three/four.html.
Для перенаправления URL-адресов под /one на http://one.example.com выполните следующие действия:
Redirect "/one/" "http://one.example.com/"
Для перенаправления одного хост-имени на другое, например, example.com на www.example.com, см. рецепт Канонические имена хостов.
Для перенаправления http URL-адресов на https выполните следующие действия:
<VirtualHost *:80>
ServerName www.example.com
Redirect "/" "https://www.example.com/"
</VirtualHost>
<VirtualHost *:443>
ServerName www.example.com
# ... SSL configuration goes here
</VirtualHost>
Использование RewriteRule для выполнения этой задачи может быть уместно, если в том же объёме есть другие директивы RewriteRule. Это потому, что когда в одном объёме есть директивы Redirect и RewriteRule, директивы RewriteRule будут выполняться первыми, независимо от порядка их появления в файле конфигурации.
В случае перенаправления http-to-https использование RewriteRule было бы уместным, если у вас нет доступа к основному файлу конфигурации сервера и вам необходимо выполнить эту задачу в файле .htaccess вместо него.
Алиасирование URL
Директива Alias обеспечивает сопоставление URI с каталогом — обычно каталогом вне вашего DocumentRoot. Хотя такую сопоставление можно выполнить с помощью mod_rewrite, Alias является предпочтительным методом по причинам простоты и производительности.
Использование Alias
Alias "/cats" "/var/www/virtualhosts/felines/htdocs"
Использование mod_rewrite для выполнения этого сопоставления может быть уместно, когда у вас нет доступа к файлам конфигурации сервера. Alias может использоваться только в контексте сервера или виртуального хоста, а не в файле .htaccess.
Символические ссылки были бы другим способом достижения того же результата, если на вашем сервере включён Options FollowSymLinks.
Виртуальные хосты
Хотя можно обрабатывать виртуальные хосты с помощью mod_rewrite, это редко правильный подход. Создание отдельных блоков <VirtualHost> почти всегда является правильным способом. В случае большого количества виртуальных хостов рассмотрите возможность использования mod_vhost_alias для автоматического создания этих хостов.
Модули, такие как mod_macro также полезны для создания большого количества виртуальных хостов динамически.
Использование mod_rewrite для создания виртуальных хостов может быть уместно, если вы используете хостинг-услугу, которая не предоставляет вам доступ к файлам конфигурации сервера, и вы, следовательно, ограничены конфигурацией с помощью файлов .htaccess.
См. документ виртуальные хосты с mod_rewrite для получения более подробной информации о том, как вы можете это сделать, если это всё ещё кажется правильным подходом.
Простое проксирование
RewriteRule предоставляет флаг [P] для передачи переписанных URI через mod_proxy.
RewriteRule "^/?images(.*)" "http://imageserver.local/images$1" [P]
Однако во многих случаях, когда не требуется фактическое сопоставление шаблонов, как в примере, показанном выше, директива ProxyPass является лучшим выбором. Приведённый здесь пример можно переписать как:
ProxyPass "/images/" "http://imageserver.local/images/"
Обратите внимание, что независимо от того, используете ли вы RewriteRule или ProxyPass, вам по-прежнему необходимо использовать директиву ProxyPassReverse для перехвата перенаправлений, отправленных сервером-обработчиком:
ProxyPassReverse "/images/" "http://imageserver.local/images/"
Вам может потребоваться использовать RewriteRule вместо этого, если в том же объёме действуют другие RewriteRule, так как директива RewriteRule обычно выполняется до ProxyPass, и поэтому может предвосхитить то, что вы пытаетесь сделать.
Тестирование переменных окружения
mod_rewrite часто используется для выполнения определённого действия на основе наличия или отсутствия определённой переменной окружения или заголовка запроса. Это можно сделать более эффективно, используя <If>.
Рассмотрим, например, распространённый случай, когда RewriteRule используется для принудительного использования канонического хост-имени, например, www.example.com вместо example.com Это можно сделать с помощью директивы <If>, как показано здесь:
<If "req('Host') != 'www.example.com'">
Redirect "/" "http://www.example.com/"
</If>
Этот метод может использоваться для выполнения действий на основе любого заголовка запроса, заголовка ответа или переменной окружения, заменяя mod_rewrite во многих распространённых сценариях.
Обратитесь к документации по оценке выражений для получения обзора типов выражений, которые вы можете использовать в разделах <If>, и в некоторых других директивах.
© 2018 The Apache Software Foundation
Licensed under the Apache License, Version 2.0.
https://httpd.apache.org/docs/2.4/en/rewrite/avoid.html