【问题标题】:.htaccess Redirect/Rewrite rules.htaccess 重定向/重写规则
【发布时间】:2015-01-15 18:54:38
【问题描述】:

在一个网站上,我有一个 .htaccess 文件设置,用于设置有关重写 url 的规则。我所有的内容页面都是动态生成的,所以只有一个文件content.php,它基本上是根据查询参数生成页面的。然后根据主导航确定网站的链接结构。

所以在 content.php 上,它通过查看 URL 从数据库中提取页面。在幕后,URL 基本上是这样的:

www.website.com/content.php?page=my-page

但是使用重写,url 实际显示和显示如下:

www.website.com/my-page/

这很好用,除了我遇到的一个问题。您几乎可以在 /my-page/ 之前添加您想要的任何目录,并且 /my-page/ 的内容仍然会显示。例如:

www.website.com/test1/test2/test3/my-page/

显示与以下内容相同的内容:

www.website.com/my-page/

如果我想使用的实际链接是:www.website.com/section/my-page/ 如何将任何以 /my-page/ 结尾的请求重定向到 www.website.come/section/my-page/

我尝试过使用以下方法,但最终以无限循环结束

RewriteRule (.*)/my-page/?$ http://www.website.com/section/my-page/ [L,R=301]

【问题讨论】:

    标签: apache .htaccess mod-rewrite redirect


    【解决方案1】:

    替换这条规则:

    RewriteRule (.*)/my-page/?$ http://www.website.com/section/my-page/ [L,R=301]
    

    按照这个规则:

    RewriteRule ^(?!my-page/my-second-page)(?:.+?/)?(my-second-page)/?$ /my-page/$1/ [L,NC,R=302]
    
    RewriteRule ^.+?/(my-page)/?$ /$1/ [L,NC,R=302]
    

    还要在新浏览器中进行测试以避免旧的 301 缓存。

    【讨论】:

    • 我认为这可行。如果我希望“my-page”成为第一个“目录”,我将如何编写它?示例:www.website.com/my-page/ - 如果我删除上面每一行的“/section”,重定向不会不行。
    • 比如说我有两个不同的页面:my-page 和 my-second-page。我希望 my-page 的 URL 为 www.website.com/my-page/ 并且我希望 my-second-page 的 URL 为 www.website.com/my-page/my-second-page / 。如果有人输入 www.website.com/something/goes/here/my-second-page/ 应该重定向到 www.website.com/my-page/my-second-page/ - 如果有人输入 www.website .com/some/other/stuff/goes/here/my-page/ 应该重定向到 www.website.com/my-page/
    • 这条规则按原样工作:RewriteRule ^.+?/(my-page)/?$ /$1/ [L,NC,R=302] ---------- -- 但是另一条规则不能正常工作。 RewriteRule ^.+?/(my-second-page)/?$ /my-page/$1/ [L,NC,R=302] 导致无限循环。如果我去: website.com/something/here/my-second-page/ 它会重定向到 website.com/my-page/my-second-page/ 但随后进入无限循环。如果我去 website.com/my-second-page/ 该页面有效,但它不应该,它应该去 website.com/my-page/my-second-page/
    • 仍然导致 www.website.com/my-second-page/ 工作,而不是将其重定向到 www.website.com/my-page/my-second-page/ --- ------- 如果我去 website.com/this/is/a/test/my-second-page/ 那确实重定向到 website.com/my-page/my-second-page/ --- ---------如果我转到 website.com/my-page/test/my-second-page/ 然后该 URL 保持原样并且不会重定向到 website.com/my-page/my -第二页/
    • 好的,根据我的测试,一切正常。我是否正确地说我需要为我的 content.php 页面将处理的网站上的每个链接添加一个规则?
    【解决方案2】:

    您的重写 (.*) 表示任何/您/喜欢/之前/我的页面将匹配,并且您在它的末尾还有一个 301 永久重定向 R=301,这是不需要的。

    在您的 .htaccess 中,您可以在没有尾部斜杠的情况下进行重写:

    RewriteEngine On
        RewriteRule ^/section/([^/\.]+)$ /content.php?page=section&id=$1
        RewriteRule ^/([^/\.]+)$ /content.php?page=$1 [L]
    

    然后在 content.php 中:

    $page = (!isset($_GET['page'])) ? 'indexPage' : $_GET['page'];
    
    switch($page){
    
        case 'my-page':
    
     // process request for /my-page
    
        break;
    
        case 'my-other-page':
    
     // process request for /my-other-page
    
        break;
    
        case 'section':
        $section_id = (!isset($_GET['id'])) ? 'NONE' : $_GET['id'];
    
     // process /section/$section_id - i.e $section_id = my-section-1
    
        break;
    
        case 'indexPage':
    
     // process request for index page, i.e /
    
        break;
    
        default:
    
     // This should stop /the/anything/matching/my-page issue
        header("HTTP/1.0 404 Not Found");
    }
    

    在上面的 php 中,如果 $page 为空或未设置,则 $page 设置为 indexPage - 如果设置了 $page 但与 switch/case 部分中的任何内容都不匹配,则返回 404标题。

    $section_id 的处理方式相同,但如果未设置或为空,则设置为 NONE;与$page 变量一样,如果发送了$section_id 但不匹配任何内容,您也可以发送404 标头。

    【讨论】:

    • 这将如何动态完成?如果我的网站上有 100 个页面可以显示 content.php,我不想输入 100 个案例。
    • 只需更改content.php,以便通过调用您的数据库来评估$page。如果没有返回结果,那么您可以按照上述发送 404 标头。
    • 对不起,我不明白这个答案。看起来这样,我必须为网站上的每个页面手动输入一个案例。页面的唯一文本(我称之为 slug)仅存储在数据库中(例如:对于关于我们的页面,存储了 about-us)。它不存储整个 URL,只是“关于我们”。所以我没有看到这是如何自动解决任何问题的。
    • $page 不包含 URL - $page 是通过三元组 (!isset($_GET['page'])) ? 'indexPage' : $_GET['page']; 设置的。如果您的请求是 www,example.com/about-us,那么由于 Apache 重写,那么 $page 将只包含 about-us
    • 这不是给我现在遇到的同样问题吗?它从 URL 中查找 $_GET['page'],所以在这个 url (website.com/this/is/a/test/my-page/ $page 将 = "my-page",如果 url 是(website.com/a/different/test/my-page/) 所以它会产生相同的页面,它如何将 URL 重定向到正确的页面?
    【解决方案3】:

    我遇到了这个问题,在 小时 中弄乱了正则表达式,但无济于事,遵循这些答案。结果很简单。

    关闭 MutliViews

    简而言之,在您的服务器配置中,寻找类似这样的内容...

    Options -Indexes +FollowSymLinks +MultiViews
    

    ...把它改成这个...

    Options -Indexes +FollowSymLinks -MultiViews
    

    当然,该行可能看起来非常不同,具体取决于您的文件。关键是,在 MultiViews 前面放一个-

    注意:如果您在该行没有看到任何符号,只需删除 MultiViews 代替。 Apache2 对符号的使用是孤注一掷。

    如果您不能(或不想)更改服务器配置,请将此行粘贴到您的 .htaccess...

    Options -MultiViews
    

    这为我解决了问题!

    【讨论】:

      猜你喜欢
      • 2020-11-01
      • 2016-06-08
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-10-22
      • 2013-01-21
      • 1970-01-01
      相关资源
      最近更新 更多