我正在使用以下代码将所有www请求指向非wwwurl:
RewriteEngine On RewriteCond %{HTTP_HOST} ^www\.example\.org$ [NC] RewriteRule ^(.*)$ http://example.com/$1 [R=301,L]
这在我的网站根目录下的.htaccess文件里面工作的很好。
例如,
www.example.com – > example.com/
www.example.com/ – > example.com/
www.example.com/other_page – > example.com/other_page
但是,如果将相同的代码移到我的VirtualHostconfiguration中,则重写的URL将包含一个双尾斜杠。
www.example.com – > example.com//
www.example.com/ – > example.com//
www.example.com/other_page – > example.com//other_page
我通过从重写规则中删除斜线来修复它:
RewriteEngine On RewriteCond %{HTTP_HOST} ^www\.example\.org$ [NC] RewriteRule ^(.*)$ http://example.com$1 [R=301,L]
但是我不明白这个原因。 任何人知道为什么
据我了解,在.htaccess文件中,mod_rewrite在你的规则中处理的string是相对于.htaccess文件所在的目录而言的,所以它在开始时不会有/。
在VirtualHost条目中,它处理的string对于服务器的根是绝对的,因此包括/。
这使得mod_rewrite的工作方式有了细微的差别。
这里是一个有类似问题的人,解决办法:
http://forum.modrewrite.com/viewtopic.php?p=56322&sid=77f72967f59200b5b5de174440234c3a
这应该在两种情况下工作,假设我记得我的转义正确:
RewriteEngine On RewriteCond %{HTTP_HOST} ^www\.example\.org$ [NC] RewriteRule ^\/?(.*?)$ http://example.com/$1 [R=301,L]
发生这种情况是因为您正在使用(.*)捕获初始斜线,然后在新位置/$1之前应用另一个斜线。 之前没有发生过,因为mod_rewrite在每个目录上下文中运行时的行为略有不同,而不是每个服务器上下文。
您可以通过select性地预先设定斜线来避免这种情况。 另外,你可以在剩余域名的空虚拟主机中使用RedirectMatch,这样可以减less处理,并且看起来更干净。
<VirtualHost *>
ServerName example.com
ServerAlias other.example.com
..
RedirectMatch permanent ^/?(.*) http://example.com/$1
</VirtualHost>
我包括这个职位的完整性。
Apache文档解释了为什么这种行为发生得很好,是“RewriteBase”指令存在的原因。
只需在你的.htaccess文件中包含'RewriteBase'指令就可以实现你想要的结果。
例:
RewriteEngine On RewriteBase / RewriteCond %{HTTP_HOST} ^www\.example\.org$ [NC] RewriteRule ^(.*)$ http://example.com/$1 [R=301,L]
从Apache 2.2 mod_rewrite文档:
RewriteBase指令显式地设置每个目录重写的基本URL。
我的经验法则是几乎总是在.htaccess文件中使用“RewriteBase”,而不是在Apacheconfiguration中使用它。
我没有时间来处理这个问题,所以只需重写// / 🙂
RewriteCond %{THE_REQUEST} // RewriteRule ^(.*)$ http://domain.com [R=301,L]