nginx 重定向循环,从 url 中删除 index.php

Posted

技术标签:

【中文标题】nginx 重定向循环,从 url 中删除 index.php【英文标题】:nginx redirect loop, remove index.php from url 【发布时间】:2014-03-08 09:06:17 【问题描述】:

我想要像 http://example.com/whatever/index.php 这样的任何请求,执行 301 重定向到 http://example.com/whatever/

我尝试添加:

rewrite ^(.*/)index.php$ $1 permanent;

location / 
    index  index.php;

这里的问题是,这种重写在根 url 上运行,这会导致无限重定向循环。

编辑:

我需要一个通用的解决方案

http://example.com/ 应该提供文件webroot/index.php

http://example.com/index.php,应该 301 重定向到http://example.com/

http://example.com/a/index.php 应该 301 重定向到 http://example.com/a/

http://example.com/a/ 应该在webroot/a/index.php 处提供 index.php 脚本

基本上,我不想在地址栏中显示“index.php”。我有旧的反向链接,需要重定向到规范的 url。

【问题讨论】:

好吧,重定向循环是一个符合逻辑的事情,因为两个 URL 是相同的,whatever/ 将调用 index.php,因为您很可能在上面有一个 index index.php 我想 301 重定向外部 url,但在内部提供文件 index.php。我该怎么做? 【参考方案1】:

如果您的 nginx 配置文件中已经有下面提到的第一行,则无需再次重写。

index index.php index.html index.htm;

重写 ^(/.).html(?.)?$ $1$2 永久;

重写 ^/(.*)/$ /$1 永久;

try_files $uri/index.html $uri.html $uri/ $uri =404;

这将从 URL 中删除 .html,此外还将从主页或索引页面中删除“索引”。例如 - https://www.example.com/index 将更改为 https://www.example.com

【讨论】:

【参考方案2】:

很好的问题,解决方案 similar to another one I've answered on ServerFault recently,虽然这里要简单得多,而且您确切地知道自己需要什么。

您在这里想要的是仅在用户明确请求/index.php 时执行重定向,但绝不重定向任何最终由实际index.php 脚本提供服务的内部请求,如通过index 定义的那样指令。

应该这样做,避免循环:

server 
    index index.php;

    if ($request_uri ~* "^(.*/)index\.php$") 
        return 301 $1;
    

    location / 

        # ...
    

【讨论】:

很好的答案。我想知道如何在没有if() 语法的情况下,而是作为一个衬里来完成它?无论如何,现在,我对其进行了一些修改以保留查询字符串(如果有):if ($request_uri ~* "^(.*/)index\.php(?:.*)$") return 301 $1$is_args$args; 我认为应该允许在其中传递查询参数。将其更改为: if ($request_uri ~* "^(.*/)index\.php(.*)") return 301 $1$2; 不错的@Neo 为了避免出现双斜线 // 我做了一点改动 # 去除 index.php 以避免重复内容if ($request_uri ~* "^(.*/)index\.php(/?)(.*)") return 301 $1$3; @Jacob Ford 如何修改表达式以匹配 index.html 和没有 html(作为扩展名)的索引? @AndrewK — if ($request_uri ~* "^(.*/)index(\.(php|html))?/?$") return 301 $1; 【参考方案3】:

试试看

location ~ /*/index.php 
    rewrite ^/(.*)/(.*) http://www.votre_domaine.com/$1 permanent;

location /index.php 
    return 301 http://www.example.com/;

【讨论】:

【参考方案4】:

试试

location = /whatever/index.php 
    return 301 $scheme://www.example.com/whatever/;

这样做的另一个好处是 nginx 的返回比重写更快。

【讨论】:

我想要一些通用的东西:/a/index.php -301-> /a/, /b/index.php -301-> /b/

以上是关于nginx 重定向循环,从 url 中删除 index.php的主要内容,如果未能解决你的问题,请参考以下文章

解析 404 url​​ 并使用 nginx 重定向

Nginx RegEx 对多个站点进行重写或内部重定向循环

Django @login_required 使用 nginx 和 fastcgi 时导致重定向循环

从 nginx 重定向中删除端口

从 http 重定向到 https 时,从 url 中删除斜线

从 URL + 重定向中删除 .html [重复]