如何制定与 .htaccess 文件相关的重写规则

如何制定与 .htaccess 文件相关的重写规则

目前我有一个这样的.htaccess 文件。

RewriteEngine On

RewriteCond %{REQUEST_FILENAME} !-f [OR]
RewriteCond %{REQUEST_URI} ^/(always|rewrite|these|dirs)/ [NC]

RewriteRule ^(.*)$ router.php [L,QSA]

当站点文件位于 Web 服务器的 document_root 中(即domain.com/abc.php-> <DOCUMENT_ROOT>/abc.php)时,它可以正常工作。但在我们当前的设置(不可更改)中,这并不能保证。我们有时可以在文档根目录和 .htaccess 文件的文件夹之间有任意文件夹(即domain.com/something/abc.php-> <DOCUMENT_ROOT>/something/abc.php)。唯一的问题是第二个RewriteCond不再起作用。有没有办法动态检查访问的路径是否是相对于.htaccess文件的路径。

例如:

如果我有一个站点,那么文件domain.com/prefix/的目录在哪里.htaccess

NOT FORCED TO REWRITE -> domain.com/prefix/index.php
FORCED TO REWRITE -> domain.com/prefix/rewrite/index.php

如果我有一个站点,那么文件domain.com/的目录在哪里.htaccess

NOT FORCED TO REWRITE -> domain.com/index.php
FORCED TO REWRITE -> domain.com/rewrite/index.php

答案1

有一个解决方案,但是并不简单。

使用RewriteMap

我会这样做:

创建一个重写映射文件。请参阅点击此处了解更多信息这是一个非常简单的文本文件,其中包含:首先,错误的 URL没有 '/', 然后一个空格(至少)然后是正确的 url,如下所示:

ok​ /folder1/
ok /folder2/
ok /folder3/

然后是代码:

RewriteMap myfoldermap \
  dbm:/web/htdocs/yourwebsite.com/rewriterules/myfoldermap.map

RewriteCond %{REQUEST_URI} ^/([^/]+)/(.*)
# Now in '%1' there's the name of the folder
# Don't touch the URL but...
# ...check if it exists in the map file
RewriteRule (.*) - [QSA,E=FOLDERMAP:${myfoldermap:%1|notfound}]

# if the environment is neither empty or not found...
RewriteCond %{E:FOLDERMAP} !^(notfound|)$
# this means we found something...
# => apply the RewriteRule
RewriteRule ^(.*)$ router.php [L,QSA]

如果它不起作用:请阅读我常用的“两个提示”,并在您的问题中添加重写日志。

两个提示:

如果您不在托管环境中(=如果它是您自己的服务器并且您可以修改虚拟主机,而不仅仅是文件.htaccess),请尝试使用该RewriteLog指令:它可以帮助您追踪此类问题:

# Trace:
# (!) file gets big quickly, remove in prod environments:
RewriteLog "/web/logs/mywebsite.rewrite.log"
RewriteLogLevel 9
RewriteEngine On

我最喜欢的检查正则表达式的工具:

http://www.quanetic.com/Regex(不要忘记选择 ereg(POSIX)而不是 preg(PCRE)!)

答案2

被迫重写是否意味着即使请求的文件或目录存在,重写规则也应该有效?

如果是,请尽量避免创建该文件/目录。

或者将其分为两个规则:

重写规则 ^/(always|rewrite|these|dirs)/router.php [L]

RewriteCond %{REQUEST_FILENAME} !-f

RewriteCond %{REQUEST_FILENAME} !-d

重写规则 ^(.*)$ router.php [L,QSA]

答案3

如果我理解正确的话(特别是我不知道你的意思被迫重写),RewriteBase是给你的。

顺便提一句:不要使用类似的东西域名.com:-)

相关内容