【发布时间】:2020-03-08 19:29:54
【问题描述】:
我正在开发一个网站项目,www.experimonkey.com。在根目录中,我有用于实验、游戏等的目录,我一直在使用 php 动态提供这些目录。我想清理 URL,以便用户可以转到 /experiments/homemade-lava-lamp 而不是 /experiments?eid=homemade-lava-lamp。我还想要一个重定向,这样如果用户转到旧链接/experiments?eid=homemade-lava-lamp,他们将被重定向到干净链接。
我以为我已经用/experiments/.htaccess 中的以下代码找出了问题的第一部分:
RewriteEngine On
RewriteRule ^([a-zA-Z0-9\-]+)/?$ index.php?eid=$1 [L]
这适用于动态页面;但是,我后来意识到这会搞砸/experiments 文件夹中的其他真实目录。比如地址/experiments/submit(其实是/experiments/submit/index.php)重定向到/experiments/submit?eid=submit——为什么,我不知道。
而且,无论我尝试了以下代码的何种组合(以及我读过的所有其他线程和文档),我都无法将旧 URL 重定向到干净的 URL:
RewriteCond %{QUERY_STRING} eid=(.+)
RewriteRule .+ https://www.experimonkey.com/experiments/%1 [R=301]
重写引擎开启
编辑(几乎可以工作)
到目前为止,我已经解决了。现在一切正常,除了最后两部分创建了一个无限循环,我不知道如何修复它。
#Ignore existing directories and files unless has query string
RewriteCond %{QUERY_STRING} !eid=(.*)
RewriteCond %{REQUEST_FILENAME} -d [OR]
RewriteCond %{REQUEST_FILENAME} -f [OR]
RewriteCond %{REQUEST_FILENAME} -l
RewriteRule ^ - [L]
#Redirect and remove query string
RewriteCond %{QUERY_STRING} /?eid=(.*)
RewriteRule (.*) https://www.experimonkey.com/experiments/%1? [R=301,L]
#Rewrite internally to actual URL
RewriteRule ^([a-zA-Z0-9\-]+)/?$ index.php?eid=$1 [L]
【问题讨论】:
-
要检查请求的 URI 是否与物理上存在的文件或文件夹匹配,您可以使用 RewriteCond 以及
f和d标志。 -
重写保留原始查询字符串,除非您指定一个新的(即使是空的,所以只是
?),或者使用一个标志来专门防止这种情况。因此,您显示的最后一次重写应该只将您重定向到https://www.experimonkey.com/experiments/?eid=homemade-lava-lamp,然后您将陷入无限循环。 -
非常感谢!!那非常有帮助。
RewriteCond %{REQUEST_FILENAME} -d [OR] RewriteCond %{REQUEST_FILENAME} -f RewriteRule ^ - [L]似乎非常适合目录问题。不过,我仍在为重定向而苦苦挣扎。我试过RewriteRule .+ https://www.experimonkey.com/experiments/%1? [R=301],我认为这是你的建议,以及[QSD],但无济于事。 -
我刚刚编辑了我的帖子以包含更新的代码。重定向被忽略了,因为由于某种原因它注册为现有文件,所以我添加了第一行(尽管我觉得必须有更好的方法来做到这一点)。但是,现在最后两部分正在创建一个无限循环,我不知道如何修复它。
标签: apache .htaccess mod-rewrite