Не могу заставить mod_rewrite корректно (и незаметно) переписать мои URL-адреса?

Я пытаюсь создать службу сокращения URL-адресов для своего веб-сайта.

Итак, вместо:

http://www.myfullwebsitename.com/page78/this-is-a-headline/

пользователи смогут посетить:

http://abc.de/aBxf

который должен перенаправить (невидимо!) на

http://abc.de/?shorturl=aBxf

который затем 301 перенаправляет через поиск в базе данных на

http://www.myfullwebsitename.com/page78/this-is-a-headline/

Я могу легко выполнить поиск в БД и перенаправление 301. Это невидимое промежуточное перенаправление, с которым я борюсь.

Я пробовал МНОГО разных вещей, но ничего не работает. Вот что я сейчас считаю должно работать:

RewriteCond %{HTTP_HOST} ^abc.de
RewriteCond %{QUERY_STRING} ^$
RewriteRule ^/(.+)  /?shorturl=$1

Но вместо молчаливого перенаправления на

http://abc.de/?shorturl=aBxF 

он перенаправляет "шумно" (302) на

http://abc.de/aBxF/?shorturl=aBxF 

Что я делаю не так?

Благодарю вас!


person Codemonkey    schedule 22.11.2012    source источник


Ответы (2)


Есть несколько вещей, которые вы можете попробовать.

Я думаю, что ваш RewriteRule должен выглядеть так (без переадресации /):

RewriteRule ^/(.+)  ?shorturl=$1 [L]

Это должно по крайней мере остановить его от перенаправления на http://abc.de/aBxF/.

Ваше исходное правило может работать, если вы добавите:

RewriteBase /

Если бы это был я, мои правила выглядели бы так:

RewriteBase /
RewriteCond %{HTTP_HOST} ^abc.de$
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule .  /redirect.php [L]

А затем в PHP я бы использовал $_SERVER['REQUEST_URI'] для получения URL-адреса (не знаю, какой язык вы используете).

Правило может выглядеть так:

RewriteRule ^(.*)$  /redirect.php?shorturl=$1 [L]

Но я бы обязательно упомянул сценарий по имени. Часть того, что может нарушить ваши правила, зависит от того, что Apache найдет ваш индексный файл после перезаписи.

Как работают правила перезаписи Apache, как только URL-адрес перезаписывается, он фактически повторно запускает правила до тех пор, пока не будут найдены другие правила. Флаг [L] для «последнего» говорит «остановиться здесь», но все равно начинается сначала. RewriteCond с флагом !-f говорит «только если файл не существует».

person Luke    schedule 22.11.2012
comment
Ваши правила, кажется, ничего не передают в redirect.php, или я что-то неправильно понимаю? - person Codemonkey; 23.11.2012
comment
Вам не нужно - если это внутреннее перенаправление, вы можете получить исходный URL-адрес в $_SERVER['REQUEST_URI']. - person Luke; 23.11.2012
comment
Но я бы обязательно упомянул сценарий по имени. - ЭТО была проблема. Добавьте index.php, и вдруг все в порядке. Спасибо за помощь Люк. - person Codemonkey; 23.11.2012

Используйте абсолютный URL:

RewriteCond %{HTTP_HOST} ^abc.de
RewriteCond %{QUERY_STRING} ^$
RewriteRule ^(.*)$ http://abc.de/?shorturl=$1 [R=301,L]
person Jcl    schedule 22.11.2012
comment
Я не хочу 302 или 301. Я должен иметь возможность переписать этот URL без дополнительного перехода HTTP, который влечет за собой 302/301 - браузеру/пользователю не нужно знать об этом промежуточный шаг. - person Codemonkey; 23.11.2012
comment
Хорошо, я не совсем понял, потому что вы смешивали коды 301 и 302 с видимой/невидимой частью, которой нет. Я могу понять вопрос, но письмо сбивает с толку. Смотрите мою правку. - person Jcl; 23.11.2012
comment
Он не хочет жесткого перенаправления, он хочет, чтобы оно было внутренним, чего он не делает. Жесткое перенаправление происходит в его скрипте (который, как я полагаю, написан на PHP). - person Luke; 23.11.2012
comment
Этот должен быть внутренним, не так ли? У меня есть несколько подобных переписываний в некоторых приложениях (для предварительного уточнения URL-адресов), и версия URL-адреса в строке запроса никогда не отображается в браузере. - person Jcl; 23.11.2012
comment
Да, так и должно быть, JCL. Я не понимаю, что происходит. Это связано с HTTP_HOST RewriteCond, которого нет у других моих перенаправлений? Возможно, это сбивает Apache с толку, заставляя думать, что я перенаправляюсь из одного домена в другой, что, очевидно, невозможно без 301/302. Даже если я не. - person Codemonkey; 23.11.2012
comment
Это было связано с тем, что я не указал index.php при перезаписи. См. комментарии выше к ответу Люка. - person Codemonkey; 23.11.2012