.htaccess 通配符子目录到单个子目录

问题描述 投票:0回答:1

我正在创建一个多租户项目,其地址结构如下

https://example.com/TENANTNAME/file.php
https://example.com/TENANTNAME/api/file.php
https://example.com/TENANTNAME/assets/js/main.js

并将其重写到单个子文件夹,例如 /BASE/ - 这个想法是我可以拥有一组文件,然后检查 URL 以找出其余部分。

谢谢你

我确实通过以下方式使其工作到了一定程度,但进一步的子文件夹(从子域编辑)未正确重定向,因此主index.php很好,但资产文件夹中的任何内容都给出了服务器错误

RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_URI} !^/BASE/(.*)/
RewriteRule ^(.*)/(.*)$ /BASE/$2 [L]

作为示例,我期望进行以下内部重写

https://example.com/TENANTNAME/index.php

https://example.com/BASE/index.php

https://example.com/TENANTNAME/assets/js/main.js

https://example.com/BASE/assets/js/main.js

index.php 示例确实符合我的尝试,但是带有更多子文件夹的资产示例则不然

apache .htaccess mod-rewrite
1个回答
0
投票

1.对现有文件或目录的测试

我的第一个问题是“磁盘上是否存在通配符文件夹?

如果是,那么前两个重写条件可能会 当请求与现有文件匹配时停止执行重写规则 或目录。

所以我认为你可以删除这些条件,因为你可能不需要 他们。

2.测试路径的第一部分

下一个重写条件,测试它不是

/BASE/
根 目录,应该足够了。但可以稍微优化一下 更换

RewriteCond %{REQUEST_URI} !^/BASE/(.*)/

RewriteCond %{REQUEST_URI} !^/BASE/

我们不需要捕获第二个斜杠后面的内容。它实际上 创建一个名为

%1
的变量,可以在重写规则中使用 目标网址。但无论如何,我们还有一些其他捕获组 在重写条件本身。

3.更改重写规则模式

它们可能是正则表达式中的贪婪小问题 重写规则。

^(.*)/
可以捕获许多字符,导致 捕获其他一些斜线。所以有两种解决方案:

  • 通过添加问号使其变得不贪婪:

    ^(.*?)/

    顺便说一句,我会将
    *
    替换为
    +
    因为我们想要匹配 至少一个字符。

  • 代替点,使用“不是斜线”:

    ^([^/]+)/

    这有一个很大的优点,因为我们知道文件夹不应该 包含斜杠字符。正则表达式应该比 上面的 ungreedy 版本也会更安全。

另外,我认为您的 PHP 脚本可能想知道什么 是重写之前的原始 URL。您可以获得这些信息 通过读取

$_SERVER
数组,但为什么不将其转换为查询 无论如何,我们捕获的参数?这可以通过以下方式实现:

RewriteRule ^([^/]+)/(.*)$ /BASE/$2?original_root=$1 [L,QSA]

第一个捕获组是

$1
,可以添加到捕获组的末尾 URL,作为查询参数。顺便说一句,重写规则模式是 应用于不带查询字符串的路径(通常添加 返回目标 URL)。但在这里,当我创建一个新查询时 字符串,我必须启用
QSA
选项,该选项将附加 原始查询字符串 新创建的查询字符串。 (QSA = query string apend)。

这样,URL 如下:

/any-folder/something/script.php?id=6&op=view

应该变成:

/BASE/something/script.php?original_root=any-folder&id=6&op=view
© www.soinside.com 2019 - 2024. All rights reserved.