Nginx 虚拟主机

[TOC]

Nginx虚拟主机配置

同一台机器上可能跑多个站点,即多个域名。在生产环境下,我们通常会配置虚拟主机来满足需求。

Nginx默认虚拟主机

默认虚拟主机 就是不管什么域名解析到该服务器上,都会访问到默认虚拟主机。

前面讲过,nginx主配置文件 ==nginx.conf== 中每一个 ==server{}== 都是一个虚拟主机(站点)。一般情况下,如果没有指定,那么第一个 ==server{}== 就是默认虚拟主机的配置。

当然, 我们还可以指定,可以在 ==server{==} 里面的 ==listen 80== 后面加上 ==default_server== ,这样就指明这个 ==server{}== 是默认虚拟主机。

1
linsten 80 default_server;        #以80端口为例

通常为了规范,并不会在主配置文件下配置好多个 ==server{}== ,而是在 ==conf== 目录下面创建 ==vhost==目录,然后在 ==vhost== 目录下创建虚拟主机的配置文件,只需要在主配置文件中加上一行:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
cat /nginx/conf/nginx.conf
user nobody;
worker_processes 8;

events {
worker_connections 1024;
}
http {
include mime.types;
default_type application/octet-stream;
sendfile on;
keepalive_timeout 65;


# server {
# listen 80;
# server_name localhost;
# location / {
# root html;
# index index.html index.htm;
# }
# error_page 500 502 503 504 /50x.html;
# location = /50x.html {
# root html;
# }
# }



include vhost/*.conf; # 新增行

}

下面来简单测试一下:

  • 创建两个server{}配置文件

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    mkdir -pv /data/wwwroot/www.1.com /data/wwwroot/www.2.com

    echo "www.1.com" > /data/wwwroot/www.1.com/index.html

    echo "www.2.com" > /data/wwwroot/www.2.com/index.html

    mkdir /usr/local/nginx/conf/vhost

    vim /usr/local/nginx/conf/vhost/www.1.com.conf #写入下面内容
    server {
    listen 80;
    server_name www.1.com;
    root /data/wwwroot/www.1.com;
    }

    vim /usr/local/nginx/conf/vhost/www.2.com.conf #写入下面内容
    server {
    listen 80;
    server_name www.2.com;
    root /data/wwwroot/www.2.com;
    }
  • 重载Nginx配置

    1
    2
    3
    4
    5
    /usr/local/nginx/sbin/nginx -t
    nginx: the configuration file /usr/local/nginx/conf/nginx.conf syntax is ok
    nginx: configuration file /usr/local/nginx/conf/nginx.conf test is successful

    /usr/local/nginx/sbin/nginx -s reload
  • 访问测试

    1
    2
    3
    4
    5
    6
    7
    8
    curl -x127.0.0.1:80 www.1.com
    www.1.com

    curl -x127.0.0.1:80 www.2.com
    www.2.com

    curl -x127.0.0.1:80 www.3.com #可以看出来,www.1.com是默认虚拟主机,虽然我们没有指定
    www.1.com

一般情况下,我们需要指定默认虚拟主机,因为不指定就是排在第一个的 ==server{}== 是默认虚拟主机,这样有点不稳定。

  • 指定默认虚拟主机

    1
    2
    3
    4
    5
    vim /usr/local/nginx/conf/vhost/default.conf             #写入下面内容
    server {
    listen 80 default_server; #指定默认虚拟主机
    deny all; #将非该服务器上的站点访问拒绝
    }
  • 访问测试

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    [root@LenovoBox ~] nginx -t
    nginx: the configuration file /usr/local/nginx/conf/nginx.conf syntax is ok
    nginx: configuration file /usr/local/nginx/conf/nginx.conf test is successful

    [root@LenovoBox ~] nginx -s reload

    [root@LenovoBox ~] curl -x127.0.0.1:80 www.3.com
    <html>
    <head><title>403 Forbidden</title></head>
    <body>
    <center><h1>403 Forbidden</h1></center> # 访问被拒绝
    <hr><center>nginx/1.16.1</center>
    </body>
    </html>

这样看起来就比较合理,服务器上没有的站点一律拒绝访问,而不是指向默认虚拟主机。

虚拟主机配置规范

一般规范来说,在主配置文件中 ==include== 虚拟主机配置文件,然后在 ==conf== 目录下创建 ==vhost== 目录,在 ==vhost==目录下定义虚拟主机配置,也就是 ==server{}== 配置部分。

上面在指定默认虚拟主机前的访问我们在 ==www.1.com.conf== 和 ==www.2.com.conf== 中没有指定index(索引页),它默认会访问 ==index.html== ,那如果指定的index不是 ==index.html== 呢?

  • 指定index

    1
    2
    3
    4
    5
    6
    7
    cat www.1.com.conf 
    server {
    listen 80;
    server_name www.1.com;
    index 2.html;
    root /data/wwwroot/www.1.com;
    }
  • 访问测试:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    nginx -s reload

    curl -x127.0.0.1:80 www.1.com
    <html>
    <head><title>403 Forbidden</title></head>
    <body>
    <center><h1>403 Forbidden</h1></center> #提示403禁止访问,索引页有个特性:找不到会提示403,而不是404
    <hr><center>nginx/1.16.1</center>
    </body>
    </html>

    echo "2.html" > /data/wwwroot/www.1.com/2.html

    curl -x127.0.0.1:80 www.1.com
    2.html #有了1.html之后就会默认访问到索引页

同时, ==server{}== 配置部分还支持域名泛解析,一个主域名下面可能会有很多个二级域名,这就会用到泛解析。

  • 指定泛解析

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    cat graped.com.conf 
    server {
    listen 80;
    server_name graped.com *.graped.com; # 连主域名一起访问到index,可以以空格分隔域名:
    root /data/wwwroot/graped.com;
    index index.html;
    }

    mkdir -pv /data/wwwroot/graped.com
    echo "graped" > /data/wwwroot/graped.com/index.html
  • 访问测试

    1
    2
    3
    4
    5
    6
    7
    8
    curl -x127.0.0.1:80 graped.com
    graped
    curl -x127.0.0.1:80 1.graped.com
    graped
    curl -x127.0.0.1:80 2.graped.com
    graped
    curl -x127.0.0.1:80 sdfasdfasdklasdopweriqweorisdaf.graped.com
    graped

基于不同端口的虚拟主机

虚拟主机不一定是监听80端口,只不过同一端口下的域名不能重复,不同端口下的域名是可以重复的。

  • 定义同端口相同域名:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    cat www.1.com.bak.conf 
    server {
    listen 80;
    server_name www.1.com;
    index index.html;
    root /data/wwwroot/www.1.com.bak;
    }

    cat www.1.com.conf
    server {
    listen 80;
    server_name www.1.com;
    index 2.html;
    root /data/wwwroot/www.1.com;
    }

    nginx -t
    nginx: [warn] conflicting server name "www.1.com" on 0.0.0.0:80, ignored #会有报错提示,server name 冲突
    nginx: the configuration file /usr/local/nginx/conf/nginx.conf syntax is ok
    nginx: configuration file /usr/local/nginx/conf/nginx.conf test is successful
  • 定义不同端口相同域名:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    cat www.1.com.conf 
    server {
    listen 80;
    server_name www.1.com;
    index 2.html;
    root /data/wwwroot/www.1.com;
    }

    cat www.1.com.bak.conf
    server {
    listen 8080;
    server_name www.1.com;
    index index.html;
    root /data/wwwroot/www.1.com.bak;
    }

    mkdir -pv /data/wwwroot/www.1.com.bak

    echo "www.1.com:8080" > /data/wwwroot/www.1.com.bak/index.html
  • 访问测试

    1
    2
    3
    4
    5
    curl -x127.0.0.1:80 www.1.com
    www.1.com

    curl -x127.0.0.1:8080 www.1.com
    www.1.com:8080