2

我有一个像这样的脏网址:http: //www.netairspace.com/photos/photo.php ?photo=3392 。我想做一些类似http://www.netairspace.com/photos/OH-LTU/Finnair_Airbus_330-202X/OUL_EFOU_Oulu/photo_3392/的事情(后来支持像http://www.netairspace.com/pic/3392这样的短网址/但我会忽略它)。

所以我有一个脚本 photo_seo_url.php,它获取照片 ID,构建 SEO URL,并进行重定向(302 用于测试,301 表示满意)。然后我计划添加 .htaccess mod_rewrite 规则,以便在调用旧 URL 时:

  • 旧 URL 将在内部重写为 photo_seo_url.php
  • photo_seo_url.php 将 301/302 重定向到 SEO URL
  • SEO URL 将在内部重写为原始 photo.php

这样,理论上,我会在获得 SEO URL 的好处的同时能够在闲暇时让旧的 URL 退休。

这些是我使用的规则:

RewriteEngine on
RewriteRule ^photos/.*/photo_([0-9]+)/?$ photos/photo.php?photo=$1 [NC,L]
RewriteCond %{QUERY_STRING} photo=([0-9]+)
RewriteRule ^photos/photo\.php$ photos/photo_seo_url.php?photo=%1 [NC,L]

但这会进入无限重定向循环。为什么,如果这两个正在进行内部重写而不是外部重定向 - 或者这就是我所缺少的?

我已经解决了添加新文件 showphoto.php 的问题,该文件只包含原始 photo.php,并更改第 2 行:

RewriteEngine on
RewriteRule ^photos/.*/photo_([0-9]+)/?$ photos/showphoto.php?photo=$1 [NC,L]
RewriteCond %{QUERY_STRING} photo=([0-9]+)
RewriteRule ^photos/photo\.php$ photos/photo_seo_url.php?photo=%1 [NC,L]

但我仍然想了解为什么原始版本会陷入无限循环。我错过或误解了一些东西。我的方法合理吗?

4

2 回答 2

3

要回答您的问题,为什么会发生此循环?这就是 SEO URI 所发生的事情GET /photos/OH-LTU/Finnair_Airbus_330-202X/OUL_EFOU_Oulu/photo_3392/,例如。

  • 规则 1 将其转换为GET /photos/photo.php?photo=3392触发内部重定向的触发内部重定向,然后重新启动.htaccess文件扫描。

  • 然后规则 2 触发将其转换为GET photos/photo_seo_url.php?photo=339触发内部重定向的内部重定向,该重定向再次重新启动.htaccess文件扫描。

  • 没有进一步的匹配发生,因此这被传递给脚本photos/photo_seo_url.php,然后执行 302 到/photos/OH-LTU/Finnair_Airbus_330-202X/OUL_EFOU_Oulu/photo_3392/并且浏览器检测到重定向循环。

您需要发生的是规则 1 触发以防止规则 2 触发,即使在内部重定向之后也是如此。一种方法是设置一个环境变量,比如 END(在下一次传递中转换为 REDIRECT_END),如果设置了则跳过规则:

RewriteEngine on
RewriteBase   /

RewriteRule   ^photos/.*/photo_([0-9]+)/?$ photos/photo.php?photo=$1 [NC,E=END:1,L]

RewriteCond   %{ENV:REDIRECT_END}:%{QUERY_STRING}   ^:photo=([0-9]+)$
RewriteRule   ^photos/photo\.php$          photos/photo_seo_url.php?photo=%1 [NC,L]

另一种方法是向noredir重写的 URI 添加一个虚拟参数并添加:

RewriteCond   %{QUERY_STRING}   !\bnoredir

到原来的第二条规则。但是,photo.php需要忽略这一点。希望这可以帮助 :-)

于 2012-06-06T15:28:19.757 回答
2
RewriteEngine on
RewriteRule ^photos/.*/photo_([0-9]+)/?$ photos/photo.php?photo=$1&rewritten [NC,L]

RewriteCond %{QUERY_STRING} !rewritten
RewriteCond %{QUERY_STRING} photo=([0-9]+)
RewriteRule ^photos/photo\.php$ photos/photo_seo_url.php?photo=%1 [NC,L]
于 2012-06-06T10:02:05.687 回答