【问题标题】:nginx conditional proxy passnginx 条件代理通过
【发布时间】:2011-12-14 06:25:11
【问题描述】:

我正在尝试配置 nginx 以代理将请求传递到另一台服务器, 仅当 $request_body 变量与特定正则表达式匹配时。

我现在的问题是,我不知道如何准确地配置这种行为。

我目前只有这个:

server {
    listen 80 default;
    server_name test.local;

    location / {
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $remote_addr;
            proxy_set_header Host $http_host;

            if ($request_body ~* ^(.*)\.test) {
                    proxy_pass http://www.google.de;
            }

            root /srv/http;
    }

}

但这里的问题是,root 总是占上风。 代理不会通过任何一种方式。

有什么想法可以做到这一点吗?

提前致谢

【问题讨论】:

  • 您确定要检查$request_body 与正则表达式吗?它会使您的应用程序慢 x 倍另外,您是要执行 proxy_pass 还是仅执行 redirect
  • 是的,很遗憾,我别无选择,而且我确实需要代理通过,应用程序无法重定向(xml-rpc 客户端)
  • 但是现在有什么问题呢?不工作吗?日志中有什么?
  • 是的,它不起作用,当我删除根行时,代理工作,当我添加根行时,就好像根本没有配置代理。
  • 所以我需要设法让 if 像我期望的那样工作......

标签: proxy nginx


【解决方案1】:

试试这个:

server {
    listen 80 default;
    server_name test.local;

    location / {
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $remote_addr;
        proxy_set_header Host $http_host;

        if ($request_body ~* ^(.*)\.test) {
            proxy_pass http://www.google.de;
            break;
        }

        root /srv/http;
    }

}

【讨论】:

  • thx 伙计,您为我节省了很多时间和头痛,我很高兴解决方案如此简单 :D 非常感谢!
  • @sharpner 这种方法还能用吗?我的测试中似乎没有。
  • @user973254 你真的测试过这个吗?看起来 nginx 在这一点上没有读取 request_body 变量,所以它永远不会通过检查...
  • 它不再起作用了。答案中唯一仍然正确的是原始版本中缺少的中断。 - 我“不接受”这个答案。
【解决方案2】:

Nginx 路由基于与请求 URI 匹配的位置指令。解决方案是临时修改它,以便将请求转发到不同的端点。

server {
    listen 80 default;
    server_name test.local;

     if ($request_body ~* ^(.*)\.test) {
         rewrite ^(.*)$ /istest/$1;
     }

     location / {
         root /srv/http;
     }

     location /istest/ {
        rewrite ^/istest/(.*)$  $1 break;

        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $remote_addr;
        proxy_set_header Host $http_host;
        proxy_pass http://www.google.de;

    }
}

if 条件只能在 Nginx 中安全地与它所属的 rewrite module 一起使用。在这个例子中。 rewrite 在请求 URI 前加上 istest 前缀。

location 块优先考虑最接近的匹配。任何与/istest/ 匹配的内容都将转到第二个块,该块使用另一个rewrite 从请求URI 中删除/istest/,然后再转发到上游代理。

【讨论】:

  • 通过这个解决方案,用户也可以直接访问/istest/,绕过“if”检查。有没有办法防止这种情况发生?
  • 客户端可以通过在请求正文中包含所需的字符串来访问 /istest/ 路径 - 所以这并不是要阻止对路径的访问。如果请求不受信任,上游服务器应验证该请求。但是,条件块中的set $my_upstream http://www.google.de; 和位置块中的proxy_pass $my_upstream; 可能会强制执行硬失败。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2023-03-11
  • 1970-01-01
  • 2018-01-07
  • 1970-01-01
  • 1970-01-01
  • 2016-01-24
  • 2014-02-13
相关资源
最近更新 更多