<返回目录     Powered by claud/xia兄

第3课: 虚拟主机配置

基于域名、IP、端口的虚拟主机

什么是虚拟主机

虚拟主机(Virtual Host)技术允许在一台物理服务器上运行多个网站。Nginx通过server块来实现虚拟主机,可以根据域名、IP地址或端口来区分不同的网站。

虚拟主机的类型

基于域名的虚拟主机

这是最常用的虚拟主机配置方式,通过server_name指令匹配不同的域名。

示例1:单域名配置

server {
    listen 80;
    server_name www.example.com;
    root /var/www/example;
    index index.html index.htm;

    access_log /var/log/nginx/example.access.log;
    error_log /var/log/nginx/example.error.log;

    location / {
        try_files $uri $uri/ =404;
    }
}

示例2:多域名配置

server {
    listen 80;
    # 多个域名指向同一个网站
    server_name www.example.com example.com www.example.net;
    root /var/www/example;
    index index.html;

    location / {
        try_files $uri $uri/ /index.html;
    }
}

示例3:通配符域名

# 匹配所有子域名
server {
    listen 80;
    server_name *.example.com;
    root /var/www/subdomains/$host;
    index index.html;

    location / {
        try_files $uri $uri/ =404;
    }
}

# 匹配特定前缀的域名
server {
    listen 80;
    server_name ~^(www\.)?(.+)$;
    root /var/www/$2;

    location / {
        try_files $uri $uri/ =404;
    }
}

示例4:多站点完整配置

# 主站 - www.example.com
server {
    listen 80;
    server_name www.example.com example.com;
    root /var/www/example;
    index index.html index.htm;

    access_log /var/log/nginx/example.access.log;
    error_log /var/log/nginx/example.error.log;

    location / {
        try_files $uri $uri/ /index.html;
    }

    location ~* \.(jpg|jpeg|png|gif|ico|css|js)$ {
        expires 7d;
    }
}

# 博客站 - blog.example.com
server {
    listen 80;
    server_name blog.example.com;
    root /var/www/blog;
    index index.php index.html;

    access_log /var/log/nginx/blog.access.log;

    location / {
        try_files $uri $uri/ /index.php?$args;
    }

    location ~ \.php$ {
        fastcgi_pass unix:/var/run/php-fpm.sock;
        fastcgi_index index.php;
        fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
        include fastcgi_params;
    }
}

# API服务 - api.example.com
server {
    listen 80;
    server_name api.example.com;

    access_log /var/log/nginx/api.access.log;

    location / {
        proxy_pass http://127.0.0.1:8000;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    }
}

基于IP的虚拟主机

当服务器有多个IP地址时,可以配置基于IP的虚拟主机。

示例5:多IP配置

# 第一个IP的网站
server {
    listen 192.168.1.100:80;
    server_name www.site1.com;
    root /var/www/site1;
    index index.html;

    location / {
        try_files $uri $uri/ =404;
    }
}

# 第二个IP的网站
server {
    listen 192.168.1.101:80;
    server_name www.site2.com;
    root /var/www/site2;
    index index.html;

    location / {
        try_files $uri $uri/ =404;
    }
}

# 监听所有IP
server {
    listen 0.0.0.0:80;
    server_name www.site3.com;
    root /var/www/site3;
    index index.html;
}

基于端口的虚拟主机

通过不同的端口区分不同的网站。

示例6:多端口配置

# 80端口 - 主站
server {
    listen 80;
    server_name example.com;
    root /var/www/main;
    index index.html;

    location / {
        try_files $uri $uri/ =404;
    }
}

# 8080端口 - 管理后台
server {
    listen 8080;
    server_name example.com;
    root /var/www/admin;
    index index.html;

    # 限制访问IP
    allow 192.168.1.0/24;
    deny all;

    location / {
        try_files $uri $uri/ =404;
    }
}

# 8081端口 - 测试环境
server {
    listen 8081;
    server_name example.com;
    root /var/www/test;
    index index.html;

    location / {
        try_files $uri $uri/ =404;
    }
}

默认虚拟主机

配置默认虚拟主机来处理未匹配的请求。

示例7:默认server配置

# 默认虚拟主机(处理所有未匹配的请求)
server {
    listen 80 default_server;
    listen [::]:80 default_server;
    server_name _;

    # 返回444状态码(关闭连接)
    return 444;
}

# 或者返回自定义页面
server {
    listen 80 default_server;
    server_name _;
    root /var/www/default;

    location / {
        return 403 "Access Denied";
    }
}

示例8:域名重定向

# 将不带www的域名重定向到带www的域名
server {
    listen 80;
    server_name example.com;
    return 301 https://www.example.com$request_uri;
}

# 主站配置
server {
    listen 80;
    server_name www.example.com;
    root /var/www/example;
    index index.html;

    location / {
        try_files $uri $uri/ =404;
    }
}

# 旧域名重定向到新域名
server {
    listen 80;
    server_name old-domain.com www.old-domain.com;
    return 301 https://new-domain.com$request_uri;
}

server_name匹配优先级

Nginx按照以下优先级匹配server_name:

  1. 精确匹配:server_name www.example.com;
  2. 前缀通配符:server_name *.example.com;
  3. 后缀通配符:server_name www.example.*;
  4. 正则表达式:server_name ~^www\.example\.com$;
  5. default_server

示例9:匹配优先级演示

# 优先级1:精确匹配
server {
    listen 80;
    server_name www.example.com;
    return 200 "精确匹配";
}

# 优先级2:前缀通配符
server {
    listen 80;
    server_name *.example.com;
    return 200 "前缀通配符匹配";
}

# 优先级3:后缀通配符
server {
    listen 80;
    server_name www.example.*;
    return 200 "后缀通配符匹配";
}

# 优先级4:正则表达式
server {
    listen 80;
    server_name ~^www\d+\.example\.com$;
    return 200 "正则表达式匹配";
}

# 优先级5:默认server
server {
    listen 80 default_server;
    server_name _;
    return 200 "默认server";
}

示例10:生产环境多站点配置

# /etc/nginx/conf.d/example.com.conf
server {
    listen 80;
    server_name example.com www.example.com;
    return 301 https://$server_name$request_uri;
}

server {
    listen 443 ssl http2;
    server_name example.com www.example.com;
    root /var/www/example/public;
    index index.php index.html;

    ssl_certificate /etc/nginx/ssl/example.com.crt;
    ssl_certificate_key /etc/nginx/ssl/example.com.key;

    access_log /var/log/nginx/example.access.log;
    error_log /var/log/nginx/example.error.log;

    add_header X-Frame-Options "SAMEORIGIN" always;
    add_header X-Content-Type-Options "nosniff" always;

    location / {
        try_files $uri $uri/ /index.php?$query_string;
    }

    location ~ \.php$ {
        fastcgi_pass unix:/var/run/php-fpm.sock;
        fastcgi_index index.php;
        fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
        include fastcgi_params;
    }

    location ~* \.(jpg|jpeg|png|gif|ico|css|js)$ {
        expires 30d;
        add_header Cache-Control "public, immutable";
    }
}
虚拟主机配置最佳实践:
常见问题:

实践练习

练习任务:
  1. 配置两个基于域名的虚拟主机(site1.local和site2.local)
  2. 为每个虚拟主机创建不同的网站根目录和首页
  3. 配置一个基于端口的虚拟主机(8080端口)
  4. 配置默认虚拟主机返回403错误
  5. 配置域名重定向(将site1.local重定向到www.site1.local)
  6. 修改本地hosts文件添加域名解析
  7. 使用浏览器访问测试各个虚拟主机
  8. 查看各个虚拟主机的访问日志

总结

虚拟主机是Nginx的核心功能之一,通过合理配置可以在一台服务器上托管多个网站。掌握基于域名、IP和端口的虚拟主机配置方法,以及server_name的匹配规则,是进行Web服务器管理的基础技能。