简体   繁体   English

Nginx将所有请求从子目录重定向到另一个子目录根目录

[英]Nginx redirect all requests from subdirectory to another subdirectory root

I'm quite new to Nginx so please bear with me. 我对Nginx很新,所以请耐心等待。

I'm trying to redirect all requests from one subdirectory (store) to the root of another subdirectory (trade). 我正在尝试将所有请求从一个子目录(存储)重定向到另一个子目录(交易)的根目录。 See my progress below. 请参阅下面的进度。 The site in the target subdirectory (trade) is a magento site so that is what most of the current rules are for. 目标子目录(交易)中的站点是一个magento站点,因此这是当前大多数规则的用途。

server {
    server_name example.com *.example.com;
    root /usr/share/nginx/html/example.com/public_html;
    index index.php index.html index.htm;

    access_log /var/log/nginx/example.access.log;
    error_log /var/log/nginx/example.error.log;

    location / {
            try_files $uri $uri/ /index.html;
    }

    location /trade/ {
            index index.html index.php;
            try_files $uri $uri/ @handler;
            expires 30d;
    }

    location ~ /store {
            rewrite /trade permanent;
    }

    location ~ ^/trade/(app|includes|lib|media/downloadable|pkginfo|report/config.xml|var)/ { internal; }
    location /trade/var/export/ { internal; }
    location /. { return 404; }
    location @handler { rewrite / /trade/index.php; }

    error_page 404 /404.html;

    error_page 500 502 503 504 /50x.html;
    location = /50x.html {
          root /usr/share/nginx/html;
    }

    # pass the PHP scripts to FastCGI server listening on 127.0.0.1:9000
    location ~ \.php$ {
            try_files $uri =404;
            fastcgi_pass unix:/var/run/php5-fpm.sock;
            fastcgi_index index.php;
            fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
            include fastcgi_params;

    }


}

The section I am using to redirect is the following: 我用来重定向的部分如下:

location ~ /store {
        rewrite /trade permanent;
}

This works for example.com/store but not example/store/index.php or any other uri with args. 这适用于example.com/store,但不适用于example / store / index.php或任何其他带有args的uri。 I have a feeling that the php file section at the bottom is overriding the processing. 我有一种感觉,底部的php文件部分覆盖了处理。 That is why I have put the ~ in front of the store location as the documentation here states this will be processed first. 这就是为什么我把〜放在商店位置的前面,因为这里的文档声明这将首先处理。 Does the processing stop or continue on? 处理是停止还是继续?

I have read about nesting a php rule but I have tried this to no avail. 我已经阅读了关于嵌套php规则的内容,但我试过这个无济于事。

I would greatly appreciate any help. 我非常感谢任何帮助。

ok try something like this 好吧尝试这样的事情

location ^~ /store(.*) {
  return 301 $scheme://$http_host/trade$1$is_args$query_string;
}

Trying to avoid hardcoded stuff as much as possible and using return because it's prefered over permanent rewrites 试图尽可能避免使用硬编码的东西并使用return,因为它优先于永久性重写

Ok, 好,

Coming back to this I can see the issue. 回到这一点,我可以看到这个问题。

In Nginx when you prepend a location directive with ~ this means that you want to process regular expressions in your directive (case sensitive, ~* for case insensitive). 在Nginx中使用〜前置位置指令时,这意味着您要在指令中处理正则表达式(区分大小写,〜*表示不区分大小写)。 I believe that all regex directives will process before any others but I stand to be corrected. 我相信所有正则表达式指令都会先于其他任何指令处理,但我有待纠正。

So when I am using: 所以当我使用时:

location ~/store {
       rewrite /trade permanent;
}

There is no regex there. 那里没有正则表达式。 Its is simply matching /store and redirecting to trade. 它只是匹配/存储和重定向到交易。

After some investigation (and polishing up on my regex, which is rubbish), I came back to it and have come up with a working solution. 经过一番调查(并对我的正则表达式进行了抛光,这是垃圾),我回过头来想出一个有效的解决方案。

location ~ ^/store/(.*) {
            rewrite ^/store(.*) /trade permanent;
    }

Here I am asking the directive to process the regex by entering ~ then match any url with /store/ in it. 在这里,我要求指令通过输入〜然后将任何url与/ store /匹配来处理正则表达式。

Then, according to the docs, the rewrite syntax is: 然后,根据文档,重写语法是:

rewrite regex replacement [ flag ] 重写正则表达式替换[flag]

so I am matching all urls with store in it and permanently redirecting them to the new subfolder. 所以我将所有url与store中的store匹配,并永久地将它们重定向到新的子文件夹。

Pretty easy really, embarrassingly so actually but hey, every day is a school day. 真的很容易,实际上很尴尬,但是嘿,每天都是上学日。 I'm open to correction on all of this and hope it helps someone. 我愿意纠正所有这些并希望它可以帮助某人。

You need to ensure that your location ~ \\.php$ handler does not take any URLs below the old folder. 您需要确保您的location ~ \\.php$ handler不会在旧文件夹下面使用任何URL。 Indeed, precedence rules are clearly documented within http://nginx.org/r/location , and you can either use regular expressions, or, better yet, use prefix-based matching with the ^~ modifier to instruct that the search must stop without trying to see if that regex-based \\.php$ location would match: 实际上,在http://nginx.org/r/location中清楚地记录了优先级规则,您可以使用正则表达式,或者更好的是,使用与^~修饰符的基于前缀的匹配来指示搜索必须停止不试图看看基于正则表达式的\\.php$ location是否匹配:

    location ^~ /old/long/path/ { # will match /old/long/path/index.php, too
        rewrite  ^/old/long/path/(.*)$  /new/$1  permanent;
    }

The above snippet is likely the most efficient way of doing this, but here is another way of doing the same: 上面的代码段可能是最有效的方法,但这是另一种方法:

    location ~ /old/long/path/(.*) {
        return  301  /new/$1$is_args$args;
    }

Why does one example has $is_args$args and the other one doesn't? 为什么一个例子有$is_args$args而另一个没有? Good question! 好问题! Note that location directive as well as the first parameter of the rewrite directive both operate based on the contents of the $uri variable, as opposed to $request_uri . 请注意, location指令以及rewrite指令的第一个参数都基于$uri变量的内容进行操作,而不是$request_uri Long story short, but $uri does not contain $args , so, in both cases, $1 will not contain any args ; 长话短说,但$uri不包含$args ,因此,在这两种情况下, $1都不包含任何args ; however, in the case of rewrite , the case is deemed so common that $args are automatically added back by nginx, unless the new string ends with a ? 但是,在rewrite的情况下,这种情况被认为是如此常见,以至于$args会被nginx自动添加回来,除非新字符串以?结尾? character, see http://nginx.org/r/rewrite . 角色,见http://nginx.org/r/rewrite

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM