Nginx的重写无www前缀的域名到www前缀的域名

问题描述:

我看到Nginx的HttpRewriteModule documentation有一个例子来重写WWW前缀的域名到非www前缀的域名:Nginx的重写无www前缀的域名到www前缀的域名

if ($host ~* www\.(.*)) { 
    set $host_without_www $1; 
    rewrite ^(.*)$ http://$host_without_www$1 permanent; # $1 contains '/foo', not 'www.mydomain.com/foo' 
} 

我怎样才能做相反的事情 - 将一个非www前缀域重写为www前缀域?我想也许我可以做如下的事情,但Nginx不喜欢嵌套的if语句。

if ($host !~* ^www\.) {      # check if host doesn't start with www. 
    if ($host ~* ([a-z0-9]+\.[a-z0-9]+)) { # check host is of the form xxx.xxx (i.e. no subdomain) 
     set $host_with_www www.$1; 
     rewrite ^(.*)$ http://$host_with_www$1 permanent; 
    } 
} 

而且我想这对任何域名的工作,而无需显式地告诉Nginx的重写domain1.com - > www.domain1.com,domain2.com - > www.domain2.com等,因为我有大量的域名需要重写。

嗯,我想我真的不需要外部的“if”语句,因为我只是检查形式为xxx.xxx的域。以下这些对我来说很有用,虽然它不健壮。让我知道是否有更好的解决方案。

if ($host ~* ^([a-z0-9\-]+\.(com|net|org))$) { 
     set $host_with_www www.$1; 
     rewrite ^(.*)$ http://$host_with_www$1 permanent; 
    } 

编辑:在正则表达式中添加了连字符,因为它是主机名中的有效字符。

+0

如何使用这个没有? – pahnin 2016-08-01 10:49:43

if ($host !~* ^www\.) { 
    rewrite ^(.*)$ http://www.$host$1 permanent; 
} 
+1

这对我不起作用,因为我不想重写像static.mydomain.com这样的子域名。我可能应该在我的问题中说明这一点。感谢您的回答。 – saltycrane 2009-11-09 18:18:45

if ($host ~* ^[^.]+\.[^.]+$) { 
    rewrite ^(.*)$ http://www.$host$1 permanent; 
} 

这是唯一可能得到有效的主机名,因为该请求将永远不会进入你的服务器,否则,因此没有必要建立自己的验证逻辑。

nginx文档警告不要使用if来重写。请在这里看到的链接:http://wiki.nginx.org/Pitfalls#Server_Name

As noted in the Nginx documentation, you should avoid using the if directive in Nginx where possible,因为只要你在你的配置有if您的服务器需要评估每一个请求,以决定是否匹配if与否。

更好的解决方案是多个服务器指令。

server { 
     listen 80; 
     server_name website.com; 
     return 301 $scheme://www.website.com$request_uri; 
} 

server { 
     listen 80; 
     server_name www.website.com; 
     ... 
} 

如果你想成为一个SSL(HTTPS)启用网站,你有或多或少的三个不同的选项。

  1. 设置多个IP地址,每个服务器伪指令监听自己的IP(或不同的端口,如果这是您的选择)。这个选项需要SSL证书website.comwww.website.com,所以要么你有一个通配符证书,一个UNI证书(多个域)或者只是两个不同的证书。
  2. 在应用程序中进行重写。
  3. 使用可怕的if指令。

There is also an option to use SNI, but I'm not sure this is fully supported as of now

+0

你的简单代码做到了。谢谢一堆! – 2013-07-22 20:35:27

+0

该解决方案还具有发送HTTP 301 Moved Permanently响应状态码的额外好处。这是一个高效,优雅和可读的解决方案。谢谢! – ndmeiri 2017-11-23 03:47:36