基于用户代理的 Nginx 重定向

won*_*ng2 23 nginx

这是我当前的 nginx 配置:

server {
  listen 90;
  server_name www.domain.com www.domain2.com;
  root /root/app;
  location / {
    try_files $uri =404;
  }
  location ~ /([-\w]+)/(\w+)/ {
    proxy_pass bla bla
  }
}
Run Code Online (Sandbox Code Playgroud)

它工作正常,都www.domain.comwww.domain2.com服务相同的内容。

现在我想补充

如果用户正在访问 www.domain.com 并且用户代理是 xxx 然后重定向到 www.domain2.com

我已经搜索并尝试了很多方法,但没有一个有效。

ser*_*com 17

有两种方法可以解决此问题。

  1. 为 www.domain.com 和 www.domain2.com 设置两个单独的“服务器”块,并将以下几行规则添加到“服务器”块 www.domain.com。这是解决此问题的推荐方法。

    if ($http_user_agent ~* "^xxx$") {
       rewrite ^/(.*)$ http://www.domain2.com/$1 permanent;
    }
    
    Run Code Online (Sandbox Code Playgroud)
  2. 如果您想使用两个域的单个“服务器”块管理重定向,请尝试以下规则

    set $check 0;
    if ($http_user_agent ~* "^xxx$") {
        set $check 1;
    }
    if ($host ~* ^www.domain.com$) {
        set $check "${check}1";
    }
    if ($check = 11) {
        rewrite ^/(.*)$ http://www.domain2.com/$1 permanent;
    }
    
    Run Code Online (Sandbox Code Playgroud)


Pot*_*thu 8

步骤 1:有两个服务器块,一个用于 domain.com 和 domain2.com。

第 2 步:如果正确使用,因为如果使用不当,它是邪恶的。

这是完整的解决方案...

server {
  listen 90;
  server_name www.domain.com;
  root /root/app;

  # redirect if 'xxx' is found on the user-agent string
  if ( $http_user_agent ~ 'xxx' ) {
    return 301 http://www.domain2.com$request_uri;
  }

  location / {
    try_files $uri =404;
  }
  location ~ /([-\w]+)/(\w+)/ {
    proxy_pass bla bla
  }
}

server {
  listen 90;
  server_name www.domain2.com;
  root /root/app;
  location / {
    try_files $uri =404;
  }
  location ~ /([-\w]+)/(\w+)/ {
    proxy_pass bla bla
  }
}
Run Code Online (Sandbox Code Playgroud)


Koe*_*en. 6

推荐的方法可能是使用 a map,也因为这些变量仅在使用时才进行评估。

此外,使用return 301 ...比重写更可取,因为不必编译正则表达式。

这是一个将主机和用户代理作为连接字符串与单个正则表达式进行比较的示例:

map "$host:$http_user_agent" $my_domain_map_host {
  default                      0;
  "~*^www.domain.com:Agent.*$" 1;
}

server {
  if ($my_domain_map_host) {
    return 302 http://www.domain2.com$request_uri;
  }
}
Run Code Online (Sandbox Code Playgroud)

这可能会更加灵活,例如,如果涉及的不是 2 个而是更多的域。

在这里,我们www.domain.com使用以Agentto开头的用户代理映射,http://www.domain2.comwww.domain2.com以确切的用户代理映射Other Agenthttp://www.domain3.com

map "$host:$http_user_agent" $my_domain_map_host {
  default                             0;
  "~*^www.domain.com:Agent.*$"        http://www.domain2.com;
  "~*^www.domain2.com:Other Agent$"   http://www.domain3.com;
}

server {
  if ($my_domain_map_host) {
    return 302 $my_domain_map_host$request_uri;
  }
}
Run Code Online (Sandbox Code Playgroud)

注意,您需要 nginx 0.9.0 或更高版本才能使 map 中的连接字符串工作。