Proxy_pass忽略端口

时间:2018-06-14 01:03:42

标签: nginx url-rewriting oracle-apex nginx-location ngx-http-rewrite-module

我有一台运行NGINX的CentOS服务器收听80和一台数据库服务于8080的应用程序。我希望能够输入

  

http://example.com/dev/abc

并实际访问

  

http://example.com:8080/apex/abchttp://localhost:8080/apex/abc

我已使用此位置配置

location /dev {
       proxy_pass http://example.com:8080/apex;
    }

然而,当我试一试时,显示的网址是

  

http://example.com/apex/apex

找不到页面,日志显示:

2018/06/14 12:51:33 [error] 7209#0: *2067 open()
"/usr/share/nginx/html/apex/apex" failed (2: No such file or directory), 
client: 124.157.113.187, server: _, request: "GET /apex/apex HTTP/1.1", host: "example.com"

看起来发生了两件奇怪的事情

1)尽管有proxy_pass

,仍然使用端口80而不是8080

2)为什么顶点两次" / apex / apex /"

请帮助:)

从配置文件中添加整个服务器块:

server {
    listen       80 default_server;
    listen       [::]:80 default_server;
    server_name  example.com;
    root         /usr/share/nginx/html;

    # Load configuration files for the default server block.
    include /etc/nginx/default.d/*.conf;

   location /dev {
       proxy_pass http://example.com:8080/apex;
    }

    error_page 404 /404.html;
        location = /40x.html {
    }

    error_page 500 502 503 504 /50x.html;
        location = /50x.html {
    }
}

更新 - 有关可能有用的应用的更多信息

该应用程序是Oracle Application Express(APEX),它在端口8080上侦听。 URL的工作方式如下:

HTTP://example.com:8080/apex/f?p=[APP]:[Page]:[Session] etc

[APP],[Page]和[Session]都是相应的数字

开发环境网址是实际的:

  

http://example.com:8080/apex/f?p=4550

这是默认设置,因此如果我尝试http://example.com:8080/apex/,则默认为http://example.com:8080/apex/f?p=4550并转到登录页面

应用编号之后的所有内容都不会发生变化,因此我希望将其替换为/ dev / http://example.com:8080/apex/f?p=4550:1 - > http://example.com/dev/:1

一旦我了解了它是如何工作的,我计划设置三个proxy_pass

  

example.com/dev - >   http://example.com:8080/apex/f?p=4550

     

example.com/desktop - >   http://example.com:8080/apex/f?p=1001

     

example.com/mobile - >   http://example.com:8080/apex/f?p=201

唯一改变的是应用程序编号。

重写对所有三个都很好,但我不希望重写在URL中可见

以下是重写:

   location ~ /dev {
       rewrite ^/dev(.*) http://smallblockpro.com:8080/apex$1 last;
    }
   location ~ /desktop/ {
       rewrite ^/desktop/(.*) http://smallblockpro.com:8080/apex/f?p=1001:$1 last;
    }

    location ~ /desktop {
       rewrite ^/desktop(.*) http://smallblockpro.com:8080/apex/f?p=1001:$1 last;
    }

    location ~ /mobile/ {
       rewrite ^/mobile/(.*) http://smallblockpro.com:8080/apex/f?p=201:$1 last;
    }

    location ~ /mobile {
       rewrite ^/mobile(.*) http://smallblockpro.com:8080/apex/f?p=201:$1 last;
    }

3 个答案:

答案 0 :(得分:0)

location ~ /desktop/ {
    rewrite ^/desktop/(.*) http://smallblockpro.com:8080/apex/f?p=1001:$1 last;
 }

之所以向用户显示:8080端口号是因为您在重写指令中使用了绝对URL,这导致NGINX直接向用户产生301 Moved响应-您的假定这样重写后它仍会通过proxy_pass,请参见http://nginx.org/r/rewrite

  
    

如果替换字符串以“ http://”,“ https://”或“ $ scheme”开头,则处理将停止并将重定向返回给客户端。

  

如果您只想在Oracle Application Express(APEX)的前端/desktop/$1和后端/apex/f?p=1001:$1之间创建映射,那么最好的方法是使用您的nginx前端服务器上的以下代码:

location /desktop/ {
    rewrite ^/desktop/?(.*)$ /apex/f?p=1001:$1 break;
    return 400;
    proxy_pass http://smallblockpro.com:8080;
}

我建议为/dev//mobile//desktop/中的每一个复制粘贴它;同样,我不建议按照ServerFault's nginx-reverse-proxy-url-rewritehow-to-remove-the-path-with-an-nginx-proxy-pass的要求保留无斜杠的版本,因为nginx已经处理了请求,而在诸如您这样的情况下却没有用斜杠结尾我在上面提出。

答案 1 :(得分:0)

这是我在ORDS / SDW(sqldev-web)开发服务器上使用的复制粘贴。

这是在房屋的REST一侧使用ORDS的基本示例。

访问权限是:

 https://xyz.oraclecorp.com/sdw/klrice/metadata-catalog/

然后将其代理为:

 https://xyz.oraclecorp.com:8083/ords/klrice/metadata-catalog/

使用此配置。除了不重写为绝对URI之外,因为这样做将进行完整的浏览器重定向,而不仅仅是重写代理通过的URL。

   location /sdw/ {
       rewrite /sdw/(.*) /ords/$1 break;
       proxy_pass https://xyz.oraclecorp.com:8083/ords/;
       proxy_redirect    off;
       proxy_set_header  Host             $http_host;
       proxy_set_header  X-Real-IP        $remote_addr;
       proxy_set_header  X-Forwarded-For  $proxy_add_x_forwarded_for;

    }

您将要面对的问题是

   rewrite ^/desktop/(.*) http://smallblockpro.com:8080/apex/f?p=1001:$1 last;

APEX将以.../apex/XYZ的身份查看和写入链接/重定向/包含(javascript / css / ...),这将影响nginx服务器,并且不知道如何处理/apex/

这是基于我上面的设置的一个示例。请注意,我对/ sdw /的请求变成了重定向到/ ords /

的位置
 wget  -S https://xyz.oraclecorp.com/sdw/
--2018-06-21 17:10:28--  https://xyz.oraclecorp.com/sdw/
Resolving xyz.oraclecorp.com... 123.456.789.123
Connecting to xyz.oraclecorp.com|123.456.789.123|:443... connected.
HTTP request sent, awaiting response... 
  HTTP/1.1 302 Found
  Server: nginx/1.12.1


  Location: https://xyz.oraclecorp.com/ords/f?p=4550:1:375440000433:::::
Location: https://xyz.oraclecorp.com/ords/f?p=4550:1:375440000433::::: [following]

因此,最简单的方法是将ords部署(/ apex /)与重写/重定向相匹配,然后使用proxy pass来内部化:8080内容。所以

location ~ /desktop/ {
       rewrite ^/desktop/(.*) http://smallblockpro.com/apex/f?p=1001:$1 last;
    }
location ~ /apex/ {
       proxy_pass http://smallblockpro.com:8080/apex/;
       proxy_redirect    off;
       proxy_set_header  Host             $http_host;
       proxy_set_header  X-Real-IP        $remote_addr;
       proxy_set_header  X-Forwarded-For  $proxy_add_x_forwarded_for;
    }

此选项将使您的用户拥有一个不错的/ desktop /入口点,但随后会为应用程序本身重定向/ apex/。

ORDS url-mappings.xml中还有一个选项可以保留/ desktop /,也可以像这样将其添加到ords的映射中,以便知道/ desktop /。然后,nginx可以对每个条目URL进行相同的代理传递。

url-mapping.xml文件内容

 <pool-config xmlns="http://xmlns.oracle.com/apex/pool-config">
    <pool name="mypool" base-path="/desktop" />
   </pool-config>

然后在nginx中

location ~ /desktop/ {
       proxy_pass http://smallblockpro.com:8080/desktop/;
       proxy_redirect    off;
       proxy_set_header  Host             $http_host;
       proxy_set_header  X-Real-IP        $remote_addr;
       proxy_set_header  X-Forwarded-For  $proxy_add_x_forwarded_for;
    }

答案 2 :(得分:-1)

在您进一步阅读之前,请阅读以下SO线程,其中解释了额外的/apex/

Nginx proxy_pass only works partially

配置中的两个问题

  1. 您需要将正确的网址传递给后端服务
  2. 您需要确保处理任何重定向并正确替换网址
  3. 以下是我认为适合你的配置

    server {
        listen       80 default_server;
        listen       [::]:80 default_server;
        server_name  example.com;
        root         /usr/share/nginx/html;
    
        # Load configuration files for the default server block.
        include /etc/nginx/default.d/*.conf;
    
       location /dev/ {
           proxy_pass http://example.com:8080/apex/;
           proxy_redirect http://example.com:8080/apex/ $scheme://$host/dev/;
        }
    
        error_page 404 /404.html;
            location = /40x.html {
        }
    
        error_page 500 502 503 504 /50x.html;
            location = /50x.html {
        }
    }