为何Directory与RewriteRule兼容而DirectoryMatch失效?
解决Apache DirectoryMatch中RewriteRule匹配绝对路径导致404的问题
核心差异说明
Directory指令下,RewriteRule的匹配目标是相对于当前目录的路径;但DirectoryMatch作为正则匹配目录的指令,其中的RewriteRule默认匹配的是文件系统绝对路径——这就是相同规则下Directory能正常工作、DirectoryMatch却返回404的原因:规则里的相对路径捕获会被替换成绝对路径的一部分,导致重写后的文件路径完全错误。
解决方案:用%{REQUEST_URI}获取相对路径
借助%{REQUEST_URI}变量(存储客户端请求的、相对于网站根目录的URL路径)提取需要重写的相对路径部分,替代RewriteRule直接匹配绝对路径的逻辑。
示例1:gzip压缩文件重写
原Directory有效规则:
<Directory /var/www/html> RewriteEngine On RewriteRule ^(.*)\.html$ $1.html.gz [L] </Directory>
改为DirectoryMatch版本:
<DirectoryMatch "^/var/www/html$"> RewriteEngine On # 捕获REQUEST_URI中.html结尾的相对路径部分 RewriteCond %{REQUEST_URI} ^/(.*)\.html$ # 用%1引用捕获的相对路径,重写到对应gz文件 RewriteRule ^.*$ %1.html.gz [L] </DirectoryMatch>
示例2:.new后缀文件重写
原Directory有效规则:
<Directory /var/www/html> RewriteEngine On RewriteRule ^(.*)$ $1.new [L] </Directory>
改为DirectoryMatch版本:
<DirectoryMatch "^/var/www/html$"> RewriteEngine On # 捕获REQUEST_URI中的完整相对路径 RewriteCond %{REQUEST_URI} ^/(.*)$ # 重写为带.new后缀的路径 RewriteRule ^.*$ %1.new [L] </DirectoryMatch>
原理解析
%{REQUEST_URI}不受DirectoryMatch的文件系统路径影响,始终返回客户端请求的相对URL(比如访问test.html时,值为/test.html)。通过RewriteCond捕获这个路径的有效部分,再在RewriteRule中用%N(N为捕获组序号)引用,就能实现和Directory指令下完全一致的相对路径重写逻辑。
内容的提问来源于stack exchange,提问作者MarkDBlackwell
相关产品推荐
相关产品推荐

