如何使用nginx通过proxy_pass转发查询字符串参数?

时间:2011-11-15 02:13:23

标签: parameters nginx

upstream apache {
   server 127.0.0.1:8080;
}
server{
   location ~* ^/service/(.*)$ {
      proxy_pass http://apache/$1;
      proxy_redirect off;
   }
 }

以上代码段会将请求包含字符串“service”的请求重定向到另一台服务器,但不包含查询参数。

7 个答案:

答案 0 :(得分:125)

来自proxy_pass文档:

  

一个特例是在proxy_pass语句中使用变量:未使用请求的URL,您自己负责自己构建目标URL。

由于您在目标中使用$ 1,因此nginx依赖于您准确地告诉它要传递的内容。您可以通过两种方式解决此问题。首先,使用proxy_pass剥离uri的开头是微不足道的:

location /service/ {
  # Note the trailing slash on the proxy_pass.
  # It tells nginx to replace /service/ with / when passing the request.
  proxy_pass http://apache/;
}

或者如果您想使用正则表达式位置,只需包含参数:

location ~* ^/service/(.*) {
  proxy_pass http://apache/$1$is_args$args;
}

答案 1 :(得分:22)

我使用~代替~*的第二种方法略微修改了kolbyjack的版本。

location ~ ^/service/ {
  proxy_pass http://apache/$uri$is_args$args;
}

答案 2 :(得分:7)

我修改了@kolbyjack代码以使其适用于

http://website1/service
http://website1/service/

带参数

location ~ ^/service/?(.*) {
    return 301 http://service_url/$1$is_args$args;
}

答案 3 :(得分:4)

你必须使用rewrite来使用proxy_pass传递params 这是我为angularjs app部署到s3

的例子

S3 Static Website Hosting Route All Paths to Index.html

根据您的需求采用

location /service/ {
    rewrite ^\/service\/(.*) /$1 break;
    proxy_pass http://apache;
}

如果你想在http://127.0.0.1:8080/query/params/

结束

如果你想在http://127.0.0.1:8080/service/query/params/结束 你需要像

这样的东西
location /service/ {
    rewrite ^\/(.*) /$1 break;
    proxy_pass http://apache;
}

答案 4 :(得分:3)

曾添加$ request_uri proxy_pass http://apache/ $ request_uri;

答案 5 :(得分:1)

github gist https://gist.github.com/anjia0532/da4a17f848468de5a374c860b17607e7

#set $token "?"; # deprecated

set $token ""; # declar token is ""(empty str) for original request without args,because $is_args concat any var will be `?`

if ($is_args) { # if the request has args update token to "&"
    set $token "&";
}

location /test {
    set $args "${args}${token}k1=v1&k2=v2"; # update original append custom params with $token
    # if no args $is_args is empty str,else it's "?"
    # http is scheme
    # service is upstream server
    #proxy_pass http://service/$uri$is_args$args; # deprecated remove `/`
    proxy_pass http://service$uri$is_args$args; # proxy pass
}

#http://localhost/test?foo=bar ==> http://service/test?foo=bar&k1=v1&k2=v2

#http://localhost/test/ ==> http://service/test?k1=v1&k2=v2

答案 6 :(得分:0)

要重定向不使用查询字符串,请在侦听端口行下的服务器块中添加以下行:

if ($uri ~ .*.containingString$) {
           return 301 https://$host/$uri/;
}

使用查询字符串:

if ($uri ~ .*.containingString$) {
           return 301 https://$host/$uri/?$query_string;
}