如何通过htaccess中的多个重写规则修改URL?

时间:2011-05-28 07:48:18

标签: apache .htaccess mod-rewrite

我想问一个问题,以了解Apache如何处理.htaccess文件中指定的重写规则。

在我的网站上,我使用了类别中页面的经典组织,每个类别都有多个部分:

http://www.mysite.com/category/section.html.

但是,没有html页面,所有内容都由pages.php中的代码处理。使用简单的重写规则,像上面这样的URL映射到:

http://www.mysite.com/pages.php?cat=category&page=section

我决定将 section1 中的某个部分重命名为 section1-xxx 。为了提供旧名称请求(第1部分),我添加了一个简单的规则来映射 section1-xxx.html 上的 section1.html

我在.htaccess中添加的第一条规则如下:

R1

RewriteRule ^CAT1/section1.html$ CAT1/section1-xxx.html [NC]

其中 CAT1 是类别的名称。

R2

RewriteRule ^CAT1/(.*).html$ pages.php?cat=CAT1&page=$1 [L,NC]

我的想法是应用R1然后R2。然而,当应用这些规则时,我最终得到了一个无法解释的(对于我的大脑)URL。

请求以下页面时

http://www.mysite.com/CAT1/section1.html

首先在

中转换网址
http://www.mysite.com/CAT1/section1-xxx.html/section1.html

然后在

http://www.mysite.com/pages.php?cat=CAT1&page=section1-xxx.html/section1

出于好奇,我将 L (旗帜)添加到规则R1:

RewriteRule ^CAT1/section1.html$ CAT1/section1-xxx.html [L,NC]

一切正常。现在http://www.mysite.com/CAT1/section1.html通过以下方式提供:

http://www.mysite.com/pages.php?cat=CAT1&page=section1-xxx

现在问题:

  1. 为什么在将 L 标志添加到规则R1之前我获得了该网址?
  2. L 标志应指示应用匹配规则,然后停止使用其他规则。但是,设置 L 标志后,将应用 R1 R2 。为什么?
  3. 感谢您的时间。

    此致  甲

2 个答案:

答案 0 :(得分:3)

如果我们不清楚模块的行为方式,[L]标志会产生意外结果。请注意,以下内容仅适用于.htaccess文件中使用mod_rewrite时。在httpd.conf中使用时,[L]标志的行为完全符合预期。

L标志将告诉Apache停止处理该请求的重写规则。现在经常未实现的是,它现在对新的重写文件名发出新请求,并再次开始处理重写规则。

因此,如果要在目标仍与模式匹配的情况下进行重写,则它将不会按预期运行。在这些情况下,您应该使用RewriteCond从规则中排除某个文件。

正如你解释的那样,将L添加到R1。(R1将something.html重定向到someone.html,即你将他们的html页面改为他们!)

答案 1 :(得分:1)

1)您需要R1中的起始/替换字符串

2)正如amolv所说,你有两次迭代通过重写引擎,在第一种情况下,R1和R2匹配,并且重写的url在第二次迭代中没有匹配任何规则;将L添加到R1,传入的URL在第一次迭代中仅与R1匹配,在第二次迭代中仅与R2匹配。使用R1和R2中的起始/,您不再需要R1中的L。

我想知道该部分“XXX”的内容;)