Пункт 42. Когда НЕ использовать 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
, выполните следующие действия:
Перенаправить "/one/" "http://one.example.com/"
Чтобы перенаправить одно имя хоста на другое, например
example.com
на www.example.com
, см. рецепт канонических имен хостов.
Чтобы перенаправить http
URL-адреса на https
, выполните следующие действия:
<Виртуальный хост *:80>
Имя сервера www.example.com
Перенаправление "/" "https://www.example.com/"
</ виртуальный хост>
<Виртуальный хост *:443>
Имя сервера www.example.com
# ... здесь идет конфигурация SSL
</ виртуальный хост>
Использование для выполнения этой задачи может быть целесообразным, если в той же области RewriteRule
есть другие директивы. RewriteRule
Это связано с тем, что при наличии директив Redirect
и RewriteRule
в одной области действия
RewriteRule
директивы будут выполняться первыми, независимо от порядка появления в файле конфигурации.
В случае с перенаправлением http-to-https использование
RewriteRule
будет уместно, если у вас нет доступа к основному файлу конфигурации сервера, и .htaccess
вместо этого вы обязаны выполнять эту задачу в файле.
Псевдоним URL
Директива Alias
обеспечивает сопоставление URI с каталогом — обычно это каталог за пределами вашего DocumentRoot
. Хотя это сопоставление можно выполнить с помощью mod_rewrite
,
Alias
это предпочтительный метод из соображений простоты и производительности.
Использование псевдонима
Псевдоним "/cats" "/var/www/virtualhosts/felines/htdocs"
Использование mod_rewrite
для выполнения этого сопоставления может быть целесообразным, если у вас нет доступа к файлам конфигурации сервера. Псевдоним можно использовать только в контексте сервера или виртуального хоста, а не в .htaccess
файле.
Символические ссылки — это еще один способ сделать то же самое, если вы включили их Options FollowSymLinks
на своем сервере.
Виртуальный хостинг
Хотя с помощью mod_rewrite можно работать с виртуальными хостами, это редко бывает правильным. Создание отдельных
<VirtualHost>
блоков почти всегда является правильным путем. Если у вас огромное количество виртуальных хостов, рассмотрите возможность
mod_vhost_alias
автоматического создания этих хостов.
Такие модули mod_macro
также полезны для динамического создания большого количества виртуальных хостов.
Использование mod_rewrite
для создания vitualhost может быть уместным, если вы используете услугу хостинга, которая не предоставляет вам доступ к файлам конфигурации сервера, и поэтому вы ограничены конфигурацией с использованием .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
в той же области действия действуют другие s, поскольку a
RewriteRule
обычно вступает в силу перед
ProxyPass
, и поэтому может вытеснить то, что вы пытаетесь выполнить.
Тестирование переменных среды
mod_rewrite
часто используется для выполнения определенного действия в зависимости от наличия или отсутствия определенной переменной среды или заголовка запроса. Это можно сделать более эффективно, используя
<If>
.
Рассмотрим, например, распространенный сценарий, когда
RewriteRule
используется для принудительного применения канонического имени хоста, например, www.example.com
вместо
example.com
. Это можно сделать с помощью <If>
директивы, как показано здесь:
<If "req('Host') != 'www.example.com'">
Перенаправление "/" "http://www.example.com/"
</Если>
Этот метод можно использовать для выполнения действий на основе любого заголовка запроса, заголовка ответа или переменной среды, заменяя
mod_rewrite
во многих распространенных сценариях.
В частности, смотрите документацию по оценке выражений, чтобы узнать, какие типы выражений вы можете использовать в <If>
разделах и в некоторых других директивах.