Nginx 从零到精通 - 最详细的循序渐进教程
本教程从最基础的概念开始,用生动的比喻和实际案例,帮你彻底理解 Nginx。
📚 目录
- 什么是 Nginx?为什么要学它?
- Nginx 的核心作用:反向代理和静态资源服务
- 正向代理 vs 反向代理:用最简单的方式理解
- Nginx 的架构优势:为什么它这么快?
- 从零开始配置 Nginx:基础配置详解
- 实战配置:一个完整的网站配置
- 高级功能:让 Nginx 更强大
- 高并发架构:后端如何处理海量请求
- 常见场景和最佳实践
- 总结与进阶学习
1. 什么是 Nginx?为什么要学它?
1.1 Nginx 是什么?
想象一下,你的网站就像一个大商场。用户来自四面八方,想要进入商场购物。
没有 Nginx 的时候:
- 所有用户直接冲到商场大门口
- 想买商品的、想吃饭的、想咨询的,全挤在一起
- 商场(服务器)手忙脚乱,随时可能崩溃
- 用户等待时间长,体验极差
有 Nginx 的时候:
Nginx 就像站在路口的超级智能交通警察 👮♂️
- 他看见一辆车(请求)过来,会先问:“你想去哪儿啊?”
- 如果是看商品图片 → 指挥走快速路,直接去**仓库(OSS)**拿图片,速度飞快 🖼️
- 如果要下单付款 → 指挥去收银台(后端 API) 💳
- 如果要实时聊天 → 指挥走专用通讯道(WebSocket) 💬
所有车辆井井有条,系统又快又稳!
Nginx 的核心工作:
接收用户请求 → 根据规则判断 → 把请求转发到合适的地方 → 返回结果
1.2 为什么要学 Nginx?
实际数据说话:
- 全球 40%+ 的网站使用 Nginx
- 可以轻松处理数万个并发连接
- 内存占用极少,CPU 消耗低
- 配置灵活,功能强大
学会 Nginx 能做什么?
- ✅ 让网站速度飞快
- ✅ 处理高并发访问
- ✅ 搭建负载均衡
- ✅ 实现 HTTPS 加密
- ✅ 做 API 网关
- ✅ 部署多个网站
- ✅ 优化网站性能
2. Nginx 的核心作用:反向代理和静态资源服务
Nginx 有两个最重要的能力,这是理解它的关键:
2.1 反向代理(Reverse Proxy)
什么是反向代理?
Nginx 站在你的服务器前面,替你的后端应用"接客"。
工作流程:
用户 → Nginx(80/443端口) → 后端应用(3000/8080端口) → 数据库
为什么需要反向代理?
-
统一入口
- 用户只需要记住一个域名:
www.example.com - Nginx 负责把请求转发到不同的后端服务
- 用户完全不知道背后有几台服务器
- 用户只需要记住一个域名:
-
负载均衡
- 当用户量大时,后端有多台服务器
- Nginx 可以把请求分散到不同的服务器
- 就像多个收银台,分流人群
-
SSL 终结
- Nginx 处理 HTTPS 加密解密
- 后端应用可以只用 HTTP,更简单
-
安全防护
- 隐藏后端服务器的真实 IP
- 可以在 Nginx 层做访问控制、限流等
2.2 静态资源服务(Static File Server)
什么是静态资源?
- HTML、CSS、JavaScript 文件
- 图片、字体文件
- 其他不会变化的数据文件
为什么 Nginx 适合处理静态资源?
传统方式(后端程序处理):
用户请求图片 → 后端程序读取磁盘 → 返回给用户
- ❌ 每个请求都要占用一个工作线程
- ❌ 读取磁盘很慢,线程被阻塞
- ❌ 高并发时,线程耗尽,服务器崩溃
Nginx 方式:
用户请求图片 → Nginx 直接从内存/磁盘高效读取 → 返回给用户
- ✅ 事件驱动架构,一个进程处理数万连接
- ✅ 专为 I/O 密集型任务优化
- ✅ 消耗资源极少,速度飞快
动静分离架构:
┌─────────────┐
│ 用户请求 │
└──────┬──────┘│▼
┌─────────────┐
│ Nginx │
└──────┬──────┘│┌───┴───┐│ │▼ ▼
静态资源 后端API
(图片等) (业务逻辑)
核心思想:让专业的软件做专业的事
- Nginx 擅长:高并发、静态文件、网络优化
- 后端程序擅长:业务逻辑、数据库操作、复杂计算
- 分工合作,各司其职!
3. 正向代理 vs 反向代理:用最简单的方式理解
这是很多人容易混淆的概念,我们用最生动的比喻来解释:
3.1 反向代理 - 隐藏服务端(Nginx 的核心角色)
核心特点:
- 代理的对象:服务器
- 为谁服务:为服务器端服务
- 谁不知道:客户端不知道真正的服务器是谁
比喻:前台秘书
你(客户端)想找 CEO(服务器)谈事情↓
你不直接找 CEO,而是找前台(Nginx)↓
前台根据你的需求,联系 CEO 并转达↓
你始终只接触前台,不知道 CEO 在哪个办公室
实际例子:
- 访问
www.taobao.com,你不知道背后有几百台服务器 - 你只看到 Nginx,它帮你找到真正的服务器
- 这就是反向代理:隐藏服务端
3.2 正向代理 - 隐藏客户端
核心特点:
- 代理的对象:客户端
- 为谁服务:为客户端服务
- 谁不知道:服务器不知道真正的客户端是谁
比喻:中介替身
你(客户端)想租房,但不想让房东(服务器)知道你的身份↓
你找中介(正向代理)替你去找房东↓
房东只接触了中介,不知道你是谁↓
你的真实 IP 被隐藏了
实际例子:
- 公司内网代理服务器
3.3 对比总结
| 特性 | 正向代理 | 反向代理(Nginx) |
|---|---|---|
| 代理对象 | 客户端 | 服务器 |
| 隐藏谁 | 隐藏客户端 IP | 隐藏服务器 IP |
| 典型场景 | 公司代理 | Web 服务器入口 |
| 用户感知 | 用户主动配置代理 | 用户无感知 |
记忆口诀:
- 隐藏客户端 IP → 正向代理 → 代理客户端
- 隐藏服务端 IP → 反向代理 → 代理服务端
4. Nginx 的架构优势:为什么它这么快?
4.1 两种架构模型的对比
模型一:多线程阻塞模型(传统后端)
比喻:一个厨师守一道菜
餐厅接到订单 → 分配一个厨师专门负责这道菜↓
如果这道菜需要"慢炖10分钟"(等待磁盘 I/O)↓
这个厨师就必须守在锅前等着,什么也不做(线程被阻塞)↓
在这10分钟里,这个厨师(线程)资源被完全占用,但利用率极低
特点:
- ❌ 资源浪费:线程大部分时间在等待
- ❌ 并发上限低:能雇佣的厨师(线程)数量有限
- ❌ 管理成本高:管理大量厨师,调度复杂
代表: Java Tomcat、Python Django、Apache (prefork 模式)
模型二:事件驱动异步非阻塞模型(Nginx)
比喻:一个超级厨师照顾所有锅
超级厨师面前有一个任务白板(事件循环)↓
接到订单A,需要"慢炖10分钟"↓
把锅放在火上,在白板上标记"等嘀声",立即转身处理订单B↓
处理订单B(切菜),完成后继续处理其他订单↓
当某个锅发出"嘀"声(事件通知,如磁盘数据准备好了)↓
看一下白板,找到对应订单,回来进行下一步操作(装盘)
特点:
- ✅ 极高的并发能力:一个厨师能同时照顾成千上万个订单
- ✅ 资源消耗极低:只需要很少的进程/线程
- ✅ 天生为 I/O 密集型而生:完美解决等待问题
代表: Nginx、Node.js、Go
4.2 技术对比表格
| 特性 | 多线程阻塞模型 | 事件驱动异步非阻塞模型 |
|---|---|---|
| 核心架构 | 一个连接一个线程 | 单线程(或少量线程)事件循环 |
| I/O 处理 | 阻塞式:线程发起 I/O 请求后,被挂起等待 | 非阻塞式:发起请求后,立即去做别的事 |
| 并发能力 | 受限于线程数(几百到几千) | 极高(数万到数十万) |
| 资源消耗 | 高(每个线程需要独立栈内存) | 低(只需维护连接状态) |
| 适用场景 | 计算密集型(如图像处理) | I/O 密集型(如 Web 服务器) |
| 编程复杂度 | 相对简单,线性思维 | 相对复杂,需要异步编程 |
4.3 为什么 Nginx 这么快?
1. 事件驱动架构
- 一个进程处理数万连接
- 没有线程切换的开销
- 内存占用极少
2. 专为网络优化
- 零拷贝技术
- TCP 优化
- 高效的缓存机制
3. 异步非阻塞 I/O
- 读取文件时不会阻塞
- 立即处理其他请求
- 数据准备好后再返回
实际性能对比:
传统后端程序:处理 1000 个并发连接需要 2GB 内存
Nginx:处理 10000 个并发连接只需要 100MB 内存
5. 从零开始配置 Nginx:基础配置详解
5.1 Nginx 配置文件结构
Nginx 的配置通常分为两部分:
- 主配置文件 (
nginx.conf):全局设置 - 站点配置文件 (
/etc/nginx/conf.d/*.conf):具体网站的配置
5.2 主配置文件 (nginx.conf) 详解
这是整个 Nginx 的"工作手册",定义了全局规则:
# ========================================
# 1. 工作进程数
# ========================================
worker_processes auto;
# 说明:
# - auto 表示根据 CPU 核心数自动设置
# - 如果你的服务器是 4 核 CPU,就会启动 4 个工作进程
# - 这样能充分利用多核 CPU 的性能# ========================================
# 2. 事件模块配置
# ========================================
events {worker_connections 1024;# 说明:# - 每个工作进程同时能处理 1024 个连接# - 如果你的服务器是 4 核,理论上可以处理 4 × 1024 = 4096 个并发连接# - 这个数字可以根据实际情况调整
}# ========================================
# 3. HTTP 模块配置(核心配置区域)
# ========================================
http {# 3.1 性能优化三件套sendfile on;# 说明:使用最高效的方式传送文件(零拷贝技术),特别是大文件tcp_nopush on;# 说明:让数据包塞满了再发,提高网络传输效率tcp_nodelay on;# 说明:但对于小数据包(如实时消息),立即发送,不等待# 3.2 压缩配置gzip on;gzip_types text/plain text/css application/json application/javascript;gzip_min_length 1000;# 说明:# - 开启 gzip 压缩,把文本文件压缩后再发送# - 相当于把货物打包压缩,传输更快# - 通常可以压缩到原来的 30-70%# 3.3 日志格式log_format main '$remote_addr - $remote_user [$time_local] "$request" ''$status $body_bytes_sent "$http_referer" ''"$http_user_agent" "$http_x_forwarded_for"';access_log /var/log/nginx/access.log main;# 说明:记录访问日志,方便排查问题# 3.4 包含站点配置文件include /etc/nginx/conf.d/*.conf;# 说明:读取 conf.d 目录下所有 .conf 文件# 这样可以把不同网站的配置分开,便于管理
}
小结: 这部分定义了全局基调,比如用多少人工作、怎么干活最省力、怎么传输最快。
5.3 核心概念解释
worker_processes
- 作用:定义 Nginx 启动多少个工作进程
- auto:自动根据 CPU 核心数设置(推荐)
- 数字:手动指定,如
worker_processes 4;
worker_connections
- 作用:每个工作进程能处理的最大连接数
- 计算公式:最大并发数 = worker_processes × worker_connections
- 示例:4 进程 × 1024 连接 = 4096 并发
sendfile
- 作用:使用操作系统的高效文件传输机制
- 效果:减少用户态和内核态之间的数据拷贝,大幅提升性能
gzip
- 作用:压缩响应内容,减少网络传输量
- 效果:通常可减少 30-70% 的传输大小
- 适用:文本文件(HTML、CSS、JS、JSON 等)
6. 实战配置:一个完整的网站配置
现在我们来配置一个完整的网站,包含所有常用场景。
6.1 场景说明
假设我们要部署一个 Vue 3 + Node.js 的前后端分离应用:
- 前端:Vue 3 单页应用,构建后的文件在
/var/www/my-app/dist/ - 后端 API:Node.js 服务运行在
localhost:3000 - WebSocket:实时聊天功能运行在
localhost:3001 - 域名:
www.example.com - 要求:支持 HTTPS,强制跳转
6.2 完整配置代码
创建文件:/etc/nginx/conf.d/my-app.conf
# ========================================
# 1. 定义后端服务(upstream)
# ========================================
upstream backend_api {# 主要的后端服务server localhost:3000;# 备用服务(可选)# server localhost:3001 backup;# 负载均衡策略(可选)# - 默认:轮询(round-robin)# - ip_hash:根据 IP 哈希,让同一用户总是访问同一服务器# - least_conn:最少连接数
}# ========================================
# 2. HTTP 强制跳转到 HTTPS
# ========================================
server {listen 80;server_name www.example.com example.com;# 将所有 HTTP 请求重定向到 HTTPSreturn 301 https://$server_name$request_uri;# 说明:# - 301 是永久重定向# - $server_name:当前域名# - $request_uri:完整的请求路径(包括参数)# - 作用:保证所有流量都走加密通道
}# ========================================
# 3. HTTPS 主配置(核心部分)
# ========================================
server {# 监听 443 端口(HTTPS)listen 443 ssl http2;server_name www.example.com example.com;# SSL 证书配置ssl_certificate /etc/nginx/ssl/cert.pem;ssl_certificate_key /etc/nginx/ssl/key.pem;ssl_protocols TLSv1.2 TLSv1.3;ssl_ciphers HIGH:!aNULL:!MD5;# ========================================# 4. 静态资源:首页和前端文件# ========================================location = / {# 精确匹配根路径alias /var/www/my-app/dist/current/;index index.html;# 缓存设置:5 分钟内不重复请求expires 5m;add_header Cache-Control "public, max-age=300";# 说明:# - alias:指定文件路径# - expires:告诉浏览器缓存多久# - 适用于单页应用的首页}# ========================================# 5. 静态资源:公共资源(JS、CSS、图片等)# ========================================location /assets/ {alias /var/www/my-app/dist/shared-assets/;# 长期缓存:一年内有效expires 1y;add_header Cache-Control "public, max-age=31536000, immutable";# 说明:# - 这些资源文件名通常带哈希(如 app.abc123.js)# - 内容不会变,可以长期缓存# - 大幅提升页面加载速度}# ========================================# 6. API 请求:代理到后端服务# ========================================location /api/ {# 代理到后端服务proxy_pass http://backend_api;# 传递原始请求头信息proxy_set_header Host $host;proxy_set_header X-Real-IP $remote_addr;proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;proxy_set_header X-Forwarded-Proto $scheme;# 超时设置proxy_connect_timeout 60s;proxy_send_timeout 60s;proxy_read_timeout 60s;# 禁止缓存 API 响应add_header Cache-Control "no-store, no-cache, must-revalidate, proxy-revalidate";# 说明:# - proxy_pass:转发请求到后端# - proxy_set_header:把用户的真实 IP 等信息传给后端# - API 响应通常不能缓存,因为数据实时变化}# ========================================# 7. WebSocket 支持# ========================================location /ws/ {proxy_pass http://localhost:3001;# WebSocket 必需的头信息proxy_http_version 1.1;proxy_set_header Upgrade $http_upgrade;proxy_set_header Connection "upgrade";# WebSocket 保持连接proxy_set_header Host $host;proxy_read_timeout 86400; # 24 小时# 说明:# - Upgrade:协议升级标志# - Connection:升级连接# - 这样就从普通的 HTTP 请求升级为 WebSocket 长连接}# ========================================# 8. 健康检查端点# ========================================location /health {access_log off;return 200 "OK\n";add_header Content-Type text/plain;# 说明:# - 监控系统可以通过这个端点检查 Nginx 是否正常运行# - 返回 200 状态码表示健康}# ========================================# 9. 单页应用(SPA)路由支持# ========================================location / {root /var/www/my-app/dist/current;index index.html;# 关键配置:支持前端路由try_files $uri $uri/ /index.html;# 说明:# - 对于 Vue Router 的 history 模式很重要# - 当用户直接访问 /about 时,服务器没有 about.html 文件# - try_files 会先尝试找文件,找不到就返回 index.html# - 前端 JavaScript 会根据 URL 渲染对应的页面}# ========================================# 10. 错误页面# ========================================error_page 404 /404.html;error_page 500 502 503 504 /50x.html;location = /50x.html {root /var/www/my-app/dist/current;}
}
6.3 配置要点解析
location 匹配规则
location = / # 精确匹配,只有 / 才能匹配
location / # 前缀匹配,所有路径都能匹配(优先级最低)
location /api/ # 前缀匹配,只有 /api/ 开头的路径匹配
location ~ \.js$ # 正则匹配,以 .js 结尾的文件
匹配优先级:
- 精确匹配
= - 前缀匹配(最长匹配优先)
- 正则匹配
~ - 通用匹配
/
proxy_pass 路径处理
# 情况一:proxy_pass 后面有路径
location /api/ {proxy_pass http://backend_api/; # 注意末尾的 /
}
# 请求 /api/users → 转发为 http://backend_api/users# 情况二:proxy_pass 后面没有路径
location /api/ {proxy_pass http://backend_api; # 没有末尾的 /
}
# 请求 /api/users → 转发为 http://backend_api/api/users
重要: 末尾的 / 会影响路径的处理方式!
7. 高级功能:让 Nginx 更强大
7.1 灰度发布(A/B 测试)
场景: 想推新版本,但不敢让所有用户一下子都体验,先用一部分用户测试。
方法一:按 IP 分流
server {listen 443 ssl;server_name www.example.com;location / {# 如果是公司内部 IP,走新版本if ($remote_addr ~* ^192\.168\.1\.) {alias /var/www/my-app/dist/beta/;break;}# 其他用户走稳定版本alias /var/www/my-app/dist/current/;}
}
方法二:按 Cookie 分流
location / {# 如果用户有 beta 标记的 Cookie,走新版本if ($cookie_version = "beta") {alias /var/www/my-app/dist/beta/;break;}# 默认走稳定版本alias /var/www/my-app/dist/current/;
}
实际应用:
- 内部员工测试新功能
- 小比例用户参与测试
- 逐步扩大范围,降低风险
7.2 限流保护(Rate Limiting)
场景: 防止恶意刷单或者流量太大把系统冲垮。
配置步骤
第一步:定义限流区域
http {# 定义限流规则limit_req_zone $binary_remote_addr zone=api_limit:10m rate=10r/s;# 说明:# - zone=api_limit:区域名称# - 10m:分配 10MB 内存存储状态# - rate=10r/s:每秒允许 10 个请求# - $binary_remote_addr:按 IP 地址限流
}
第二步:应用限流规则
location /api/ {# 应用限流limit_req zone=api_limit burst=20 nodelay;# 说明:# - burst=20:允许突发 20 个请求排队# - nodelay:排队请求不延迟,有机会立即处理proxy_pass http://backend_api;
}
效果:
- 正常情况下:每秒最多 10 个请求
- 突发情况:允许 20 个请求排队,超过的直接返回 503(服务不可用)
7.3 防盗链(Hotlink Protection)
场景: 防止别的网站直接盗用你服务器上的图片,浪费你的流量和带宽费用。
location /images/ {# 只允许来自自己网站的请求valid_referers www.example.com example.com;# 如果来源不合法,拒绝访问if ($invalid_referer) {return 403;}# 正常返回图片alias /var/www/my-app/images/;
}
说明:
valid_referers:定义合法的来源网站$invalid_referer:如果来源不在列表中,这个变量为真- 返回 403:禁止访问
7.4 日志分析
访问日志格式:
log_format detailed '$remote_addr - $remote_user [$time_local] ''"$request" $status $body_bytes_sent ''"$http_referer" "$http_user_agent" ''rt=$request_time uct="$upstream_connect_time" ''uht="$upstream_header_time" urt="$upstream_response_time"';access_log /var/log/nginx/access.log detailed;
日志字段说明:
$remote_addr:客户端 IP$request:请求方法和路径$status:响应状态码$request_time:请求处理时间$upstream_response_time:后端响应时间
使用工具分析:
goaccess:实时日志分析awstats:详细的访问统计ELK Stack:企业级日志分析
8. 高并发架构:后端如何处理海量请求
Nginx 只是整个系统的一部分,完整的后端架构是这样的:
8.1 完整的架构图
┌─────────────┐│ 用户请求 │└──────┬──────┘│┌──────▼──────┐│ 负载均衡器 │ ← Nginx│ (Nginx/LB) │└──────┬──────┘│┌──────────────┼──────────────┐│ │ │┌─────▼─────┐ ┌─────▼─────┐ ┌─────▼─────┐│ 应用服务器1 │ │ 应用服务器2 │ │ 应用服务器3 │└─────┬─────┘ └─────┬─────┘ └─────┬─────┘│ │ │└──────────────┼──────────────┘│┌──────▼──────┐│ 缓存层 │ ← Redis└──────┬──────┘│┌──────▼──────┐│ 数据库 │ ← MySQL 主从└─────────────┘
8.2 四道防线详解
防线一:负载均衡(分散压力)
比喻:多开几个窗口
一家网红奶茶店,只有 1 个窗口肯定挤爆。多开 3 个窗口,安排一个领班在门口指挥:“你排 1 号窗,你排 2 号窗…”
技术实现:
upstream backend {server 192.168.1.10:8080; # 服务器1server 192.168.1.11:8080; # 服务器2server 192.168.1.12:8080; # 服务器3# 负载均衡策略# - 默认:轮询(round-robin)# - ip_hash:同一用户总是访问同一服务器# - least_conn:最少连接数
}server {location /api/ {proxy_pass http://backend;}
}
效果: 将压力从 1 台服务器分散到多台服务器
防线二:缓存(加快速度)
比喻:畅销品预备
"珍珠奶茶"卖得最好,提前做好 20 杯放在保温柜里。顾客要,直接付钱拿走,1 秒都不用等。
缓存层次:
-
浏览器缓存
- Nginx 设置
expires头 - 静态资源缓存 1 年
- Nginx 设置
-
CDN 缓存
- 图片、CSS、JS 放到 CDN
- 全球各地都有节点,就近访问
-
Nginx 缓存
proxy_cache_path /var/cache/nginx levels=1:2 keys_zone=api_cache:10m;location /api/ {proxy_cache api_cache;proxy_cache_valid 200 5m; # 缓存 200 响应 5 分钟proxy_pass http://backend; } -
Redis 缓存
- 应用层缓存热点数据
- 如用户信息、商品详情、秒杀库存
效果: 大量请求直接从缓存返回,不经过数据库
防线三:消息队列(削峰填谷)
比喻:扫码下单
人实在太多,堵在柜台前。店里推出扫码下单,顾客不用挤在柜台,找个地方坐下,手机点单付款。订单在后厨打印机按顺序出来,厨师慢慢做。
技术实现:
用户请求 → 应用服务器 → 快速返回(任务已提交)↓消息队列(RabbitMQ/Kafka)↓后台 Worker 慢慢处理
适用场景:
- 发送邮件
- 处理视频转码
- 生成报表
- 任何耗时但不紧急的任务
效果: 保证接口快速响应,后台慢慢处理任务
防线四:数据库优化(不拖后腿)
比喻:后厨分工
后厨就一个厨师,又要煮珍珠,又要切水果,又要泡茶,忙不过来。老板分工:
- A 厨师:专门负责写配方和记录(主数据库,负责写)
- B、C、D 厨师:专门负责读配方和看订单(从数据库,负责读)
技术实现:
-
读写分离
写操作 → 主数据库(MySQL Master) 读操作 → 从数据库(MySQL Slave)× N 台 -
分库分表
用户表 → 根据用户 ID 哈希 → 分散到 10 个数据库 -
使用 NoSQL
- Redis:缓存、计数器
- MongoDB:文档存储
- Elasticsearch:全文搜索
效果: 数据库不再是瓶颈
8.3 完整流程示例
一个用户请求的完整旅程:
1. 用户访问 www.example.com/api/products↓
2. 请求到达 Nginx(负载均衡器)↓
3. Nginx 根据负载均衡策略,选择应用服务器2↓
4. 应用服务器2 接收请求↓
5. 先查 Redis 缓存,有数据吗?├─ 有 → 直接返回(结束)└─ 没有 → 继续↓
6. 查询数据库(读库1)↓
7. 把结果存入 Redis(下次直接用)↓
8. 返回给 Nginx↓
9. Nginx 返回给用户
整个过程中:
- 静态资源(图片)直接从 Nginx 返回
- API 请求经过负载均衡、缓存、数据库优化
- 耗时任务丢到消息队列异步处理
9. 常见场景和最佳实践
9.1 场景一:前后端分离部署
需求:
- 前端:Vue 3 构建的静态文件
- 后端:Spring Boot API
- 同一台服务器部署
配置要点:
server {listen 80;server_name www.example.com;# 前端静态文件location / {root /var/www/frontend/dist;index index.html;try_files $uri $uri/ /index.html; # SPA 路由支持}# 后端 APIlocation /api/ {proxy_pass http://127.0.0.1:8080;proxy_set_header Host $host;proxy_set_header X-Real-IP $remote_addr;}
}
最佳实践:
- ✅ 前端文件由 Nginx 直接提供(高效)
- ✅ API 请求代理到后端(解耦)
- ✅ 支持 SPA 路由(用户体验好)
9.2 场景二:多个网站(虚拟主机)
需求: 一台服务器部署多个网站
配置方法:
# 网站1:www.example.com
server {listen 80;server_name www.example.com;root /var/www/site1;index index.html;
}# 网站2:www.another.com
server {listen 80;server_name www.another.com;root /var/www/site2;index index.html;
}# 默认网站(匹配所有未定义的域名)
server {listen 80 default_server;server_name _;return 444; # 关闭连接
}
最佳实践:
- ✅ 每个网站一个配置文件,便于管理
- ✅ 使用
default_server处理未定义域名 - ✅ 使用不同域名区分网站
9.3 场景三:文件上传大小限制
http {# 设置客户端请求体最大大小client_max_body_size 50M;server {# 也可以针对特定 location 设置location /upload/ {client_max_body_size 100M;proxy_pass http://backend;}}
}
9.4 场景四:跨域问题(CORS)
如果后端已经设置了 CORS,Nginx 不需要额外配置。但如果需要在 Nginx 层处理:
location /api/ {# 允许的源add_header Access-Control-Allow-Origin $http_origin always;# 允许的方法add_header Access-Control-Allow-Methods "GET, POST, PUT, DELETE, OPTIONS" always;# 允许的头部add_header Access-Control-Allow-Headers "Authorization, Content-Type" always;# 预检请求处理if ($request_method = 'OPTIONS') {return 204;}proxy_pass http://backend;
}
9.5 场景五:HTTP/2 和 HTTPS
现代网站标配:
server {# 启用 HTTP/2(需要 HTTPS)listen 443 ssl http2;server_name www.example.com;# SSL 证书ssl_certificate /etc/nginx/ssl/cert.pem;ssl_certificate_key /etc/nginx/ssl/key.pem;# 安全配置ssl_protocols TLSv1.2 TLSv1.3;ssl_ciphers HIGH:!aNULL:!MD5;ssl_prefer_server_ciphers on;# HSTS(可选)add_header Strict-Transport-Security "max-age=31536000" always;
}
HTTP/2 优势:
- ✅ 多路复用(一个连接处理多个请求)
- ✅ 服务器推送
- ✅ 头部压缩
- ✅ 更快的页面加载速度
9.6 场景六:静态资源 CDN
架构:
用户 → CDN(全球节点) → 源站(Nginx)
Nginx 配置(源站):
location /static/ {# 设置 CORS,允许 CDN 访问add_header Access-Control-Allow-Origin *;# 设置缓存头expires 1y;add_header Cache-Control "public, immutable";alias /var/www/static/;
}
10. 总结与进阶学习
10.1 核心知识点回顾
-
Nginx 是什么
- 高性能 Web 服务器
- 反向代理服务器
- 静态资源服务专家
-
核心概念
- 反向代理 vs 正向代理
- 事件驱动异步非阻塞架构
- 负载均衡
- 动静分离
-
基础配置
- worker_processes
- worker_connections
- location 匹配规则
- proxy_pass 转发
-
高级功能
- 灰度发布
- 限流保护
- 防盗链
- 缓存优化
-
高并发架构
- 负载均衡
- 多层缓存
- 消息队列
- 数据库优化
10.2 进阶学习方向
1. Nginx + Lua(OpenResty)
- 使用 Lua 脚本扩展 Nginx 功能
- 实现复杂的业务逻辑
- 性能极高,广泛应用
2. Kubernetes Ingress Controller
- 在 K8s 环境中使用 Nginx
- 动态服务发现
- 自动 SSL 证书管理
3. 性能调优
- 深入理解事件模型
- 内存优化
- 网络优化
4. 监控和日志分析
- Prometheus + Grafana
- ELK Stack
- 实时监控指标
10.3 实践建议
-
循序渐进
- 先从简单的静态网站开始
- 再学习反向代理
- 最后掌握高级功能
-
多实践
- 本地搭建测试环境
- 尝试不同配置
- 观察日志和性能
-
参考官方文档
- Nginx 官方文档
- 配置示例丰富
- 权威准确
-
学习社区资源
- GitHub 上的配置文件
- 技术博客
- 实际项目案例
🎉 结语
恭喜你完成了 Nginx 的完整学习!
通过本教程,你已经掌握了:
✅ Nginx 的核心概念和原理
✅ 基础的配置方法
✅ 实战的配置技巧
✅ 高级功能的运用
✅ 高并发架构的设计思想
记住:
- Nginx 是一个工具,理解原理比记忆配置更重要
- 多实践,多思考,遇到问题多查文档
- 架构设计要结合实际情况,没有银弹
下一步:
- 在你的项目中实际使用 Nginx
- 尝试不同的配置方案
- 持续学习和优化
祝你在 Nginx 的学习路上越走越远!🚀
本文档基于实际项目经验总结,如有问题或建议,欢迎反馈。
