简体   繁体   English

在Nginx中修改$ request_uri

[英]Modify $request_uri in Nginx

I have multiple apps running on the Nginx server: 我在Nginx服务器上运行了多个应用程序:

http://example.com/app1/ctrl/view
http://example.com/app2/ctrl/view
...

I would like to assign these apps DNS like so: 我想像这样分配这些应用程序DNS:

http://app1.example.com
http://app2.example.com
...

For that I've tried the following server block: 为此,我尝试了以下服务器块:

server {
        listen 80;
        server_name app1.example.com;

        location / {
            proxy_pass http://example.com/app1/$request_uri;
        }
}

If a user is not logged in, my app would redirect to URI: 如果用户未登录,我的应用程序将重定向到URI:

app1/ctrl/user/login?_next=/app/ctrl/view

Essentially $request_uri becomes (Note doubled app1 instance): 基本上$request_uri成为(注意加倍的app1实例):

app1/app1/ctrl/user/login?_next=/app/ctrl/view

Is there a convenient way to modify $request_uri or a better method to get around this problem? 有没有一种方便的方法来修改$request_uri或更好的方法来解决这个问题?

EDIT1 EDIT1

It seems I've solved my problem with the following server block: 看来我用以下服务器块解决了我的问题:

server {
        listen 80;
        server_name app1.example.com;

        location / {

            set $new_request_uri $request_uri;

            if ($request_uri ~ ^/app1/(.+)$) {
                set $new_request_uri $1;
            }

            proxy_pass http://example.com/app1/$new_request_uri;
        }
}

If someone knows a better (or proper " Nginx ") way to do this please don't hesitate to post an answer. 如果有人知道更好(或正确的“ Nginx ”)方式,请不要犹豫,发表答案。

EDIT2 EDIT2

Based on the comments I've also tried the following: 根据评论,我也尝试了以下内容:

server {
        listen 80;
        server_name app1.example.com;

        location / {
            proxy_pass http://example.com/app1/;
            proxy_redirect /app1/ /;
        }

        location ~ ^/app1/(.+)$ {
            return 301 http://$server_name/$1;
        }
}

This one looks better on screen, as it eliminates app1 instance in the $request_uri part completely, but you must have two location blocks. 这个在屏幕上看起来更好,因为它完全消除了$request_uri部分中的app1实例,但是你必须有两个location块。

EDIT3 EDIT3

The most efficient way to solve my problem apparently is as shown in this config: 显然解决我问题的最有效方法是如下配置:

server {
        listen 80;
        server_name app1.example.com;

        location / {
            proxy_pass http://example.com/app1/;
            proxy_redirect /app1/ /;
        }

        location /app1/ {
            rewrite ^/app1(.+) $1 permanent;
        }
}

This is due to the fact, that Nginx always tries to match the longest prefix first and then (if ^~ modifier is not present) starts sequentially processing regexes until the first regex match is found. 这是因为Nginx总是首先尝试匹配最长的prefix然后(如果^~修饰符不存在)开始顺序处理regex match regexes直到找到第一个regex match Essentially this means that all regexes are processed on every request, regardless if any of these find a match, therefore it's better to have regexes inside location directives. 从本质上讲,这意味着所有正则regexes都是在每个请求上处理的,无论这些正则表中是否找到匹配项,因此最好在location指令中使用正则regexes

You don't need to go complex way. 你不需要复杂的方式。 Solution is much simpler 解决方案要简单得多

server {
        listen 80;
        server_name app1.example.com;

        location / {
            proxy_pass http://app1.example.com/app1/;
        }

        location /app1/ {
            proxy_pass http://app1.example.com/app1/;
            # or
            # rewrite ^/app1(.+) $1 permanent;
        }
}

Nginx will take care of adding /app1/ to request and strip it from Location header. Nginx将负责添加/app1/以请求并从Location标头中删除它。

See proxy_redirect directive. 请参阅proxy_redirect指令。

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

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