mod_rewrite 用于动态地将 SEO 友好链接直接映射到单个文件,无需通过前端控制器进行路由

发布于 2024-10-02 18:03:41 字数 1290 浏览 0 评论 0原文

我正在寻找一个 SEO 友好的 url 重写规则,该规则适用于任何没有前端控制器的常见 PHP 网站。它将 SEO 友好的 url 直接映射到服务器上存在的 PHP 文件,并将剩余的 URL 分支转换为标准 URL 参数。

例如:

/folder1/folder2/folder3/page/var1/val1/var2/val2/var3/val3

将映射到:

/folder1/ folder2/folder3/page.php?var1=val1&var2=val2&var3=val3

现在,这是棘手的部分。由于重写规则需要完全不知道文件夹、页面和变量的所有名称,因此需要将 URL 参数的重写基于链接上的确切位置,在该位置可以找到沿路径存在的文件。例如,考虑以下文件是否碰巧(假设)存在于文档根目录之外:/folder1/folder2.php
在这种情况下,以下重新映射是合法且可接受的:
/folder1/folder2.php?folder3=page&var1=val1&var2=val2&var3=val3

这将是许多已经存在的传统网站的最终重写规则已构建,希望其 URL 和参数立即变得 URL 友好。

我发现的唯一示例涉及将所有内容映射到单个前端控制器或规则中预期存在的其他硬编码文件,而不是让 mod_rewrite 动态检测它们的存在。它们是相关的,但对于发现存在的任何文件来说并不灵活:

I'm looking for an SEO friendly url rewrite rule that would work for any common PHP site that doesn't have a front controller. It would map the SEO friendly url directly to the PHP file that is found to exist on the server and convert the remaining URL branches to standard URL parameters.

For example:

/folder1/folder2/folder3/page/var1/val1/var2/val2/var3/val3

would map to:

/folder1/folder2/folder3/page.php?var1=val1&var2=val2&var3=val3

Now, here's the tricky part. Since the rewrite rules need to be completely agnostic to all the names of folders, pages, and variables, it would need to base the rewrite of the URL parameters on the exact location along link where can be found a file that exists along the path. For instance, consider if the following file happened to exist (hypothetically) off the document root: /folder1/folder2.php
In this case, the following remapping would be legitimate and acceptable:
/folder1/folder2.php?folder3=page&var1=val1&var2=val2&var3=val3

This would be the ultimate rewrite rule for many traditional websites that have already been built that want their URLs and parameters to instantly become URL-friendly.

The only examples that I have found involve mapping everything to work with a single front controller or otherwise hard-coded files in the rule that are expected to exist rather than have mod_rewrite detect their existence dynamically. They're related, but not flexible for any file that is found to exist:

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

别挽留 2024-10-09 18:03:41

Apache Web 服务器确实已经知道这样一个概念:

然后您需要调整的就是获取路径信息部分并解析它。

除此之外,如果您确实想使用 mod_rewrite 实现该行为,请尝试以下操作:

RewriteCond %{DOCUMENT_ROOT}/$0.php !-f
RewriteRule ^(.+)/([^/]+)/([^/]+)$ /$1?$2=$3 [N,QSA]
RewriteCond %{DOCUMENT_ROOT}/$0.php -f
RewriteRule .+ /$0.php [L]

The Apache web server does already know such a concept:

  • MultiViews:

    The effect of MultiViews is as follows: if the server receives a request for /some/dir/foo, if /some/dir has MultiViews enabled, and /some/dir/foo does not exist, then the server reads the directory looking for files named foo.*, and effectively fakes up a type map which names all those files, assigning them the same media types and content-encodings it would have if the client had asked for one of them by name. It then chooses the best match to the client's requirements.

  • Path Info:

    This directive controls whether requests that contain trailing pathname information that follows an actual filename (or non-existent file in an existing directory) will be accepted or rejected. The trailing pathname information can be made available to scripts in the PATH_INFO environment variable.

    For example, assume the location /test/ points to a directory that contains only the single file here.html. Then requests for /test/here.html/more and /test/nothere.html/more both collect /more as PATH_INFO.

All you then need to adjust is to take the path info part and parse it.

Besides that, if you really want to implement that behavior with mod_rewrite, try this:

RewriteCond %{DOCUMENT_ROOT}/$0.php !-f
RewriteRule ^(.+)/([^/]+)/([^/]+)$ /$1?$2=$3 [N,QSA]
RewriteCond %{DOCUMENT_ROOT}/$0.php -f
RewriteRule .+ /$0.php [L]
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文