Nginx(发音同 "engine x")是一个高性能的 HTTP 和反向代理 Web 服务器,由俄罗斯程序员 Igor Sysoev 开发,2004 年首次公开发布。凭借高并发、低内存占用、高扩展性与极强的稳定性,它已成为全球互联网架构的核心基础设施。
本文从核心架构、安装部署、配置结构、核心场景(反向代理与负载均衡)、SPA 实战、安全加固、性能优化、监控排错八个维度,带你从零到一完整掌握 Nginx,并可直接复用于生产环境。
一、为什么选择 Nginx?核心架构解析
传统的 Web 服务器(如早期的 Apache HTTP Server)通常采用 Multi-Process(多进程) 或 Multi-Threaded(多线程) 模型。每个连接都会分配一个独立的进程或线程去处理。当面对上万个并发连接时,大量的上下文切换(Context Switch)和高昂的内存开销会导致系统性能急剧下降(即著名的 C10K 问题)。
Nginx 采用了一种完全不同的设计架构:Master-Worker 进程模型 + 异步非阻塞事件驱动机制(Event-Driven)。
1. Master-Worker 进程模型
| 进程 | 职责 |
|---|---|
| Master 进程 | 不直接处理任何网络请求。负责读取并校验配置、管理 Worker 进程生命周期(接收 reload、stop、quit 等信号)、在 Worker 挂掉时自动重启新的 Worker |
| Worker 进程 | 实际处理网络请求和 I/O 事件。多个 Worker 互不干扰、独立竞争处理客户端连接。Worker 数量通常设置为 CPU 物理核心数,避免不必要的上下文切换 |
2. 异步非阻塞与 Epoll
Worker 进程内部采用基于 Linux epoll(BSD/macOS 上为 kqueue)的异步非阻塞 IO 复用模型:
- 单个 Worker 进程即可同时监听成千上万个 Socket 套接字。
- 当 Socket 上没有事件时,Worker 处于休眠或处理其他就绪事件;有数据可读写时,内核会通知 Worker 处理。
- 这种机制让 Nginx 以极低的 CPU 和内存开销(极少的线程上下文切换)轻松应对数万甚至数十万的并发连接。
一句话总结:Apache 是"一个连接一个线程",Nginx 是"一个线程管所有连接",这就是它高效的本质。
二、安装与部署
2.1 Linux 包管理器安装(推荐)
Debian / Ubuntu:
sudo apt update
sudo apt install nginx -y
CentOS / RHEL:
sudo yum install epel-release -y
sudo yum install nginx -y
安装后默认已注册 systemd 服务,直接启动并设为开机自启:
sudo systemctl start nginx
sudo systemctl enable nginx
sudo systemctl status nginx
2.2 源码编译安装(需要自定义模块时)
# 下载源码(以 1.26.x 为例,版本号以官方为准)
wget http://nginx.org/download/nginx-1.26.0.tar.gz
tar -zxvf nginx-1.26.0.tar.gz
cd nginx-1.26.0
# 配置编译参数,按需开启模块
./configure \
--prefix=/usr/local/nginx \
--with-http_ssl_module \
--with-http_stub_status_module \
--with-http_gzip_static_module \
--with-http_realip_module
make -j$(nproc)
sudo make install
# 启动
sudo /usr/local/nginx/sbin/nginx
源码编译适合需要集成第三方模块(如
ngx_http_google_filter、Lua 模块)或定制编译参数的生产场景。
2.3 Windows 环境使用
Windows 下不需要安装,直接使用官方编译好的压缩包:
- 下载
nginx-xxx.zip,解压到任意目录。 - 双击
nginx.exe或命令行进入目录执行start nginx。 - 浏览器访问
http://localhost验证。 - 常用命令(在解压目录执行):
nginx.exe -t # 检查配置语法
nginx.exe -s reload # 重载配置
nginx.exe -s stop # 快速停止
Windows 版仅用于本地开发调试,生产环境请使用 Linux。注意 Windows 版不支持
epoll,性能与 Linux 版有差距。
2.4 Docker 部署(★ 生产推荐)
用 Docker 部署 Nginx 是最干净、可复现的方式。创建项目目录并编写 docker-compose.yml:
# docker-compose.yml
services:
nginx:
image: nginx:stable-alpine
container_name: web-nginx
ports:
- "80:80"
- "443:443"
volumes:
- ./nginx.conf:/etc/nginx/nginx.conf:ro # 主配置(只读挂载)
- ./conf.d:/etc/nginx/conf.d:ro # 站点配置目录
- ./html:/usr/share/nginx/html:ro # 静态资源
- ./logs:/var/log/nginx # 日志持久化
- ./certs:/etc/nginx/certs:ro # 证书目录
restart: unless-stopped
启动与管理:
docker compose up -d # 启动
docker compose ps # 查看状态
docker exec web-nginx nginx -t # 校验容器内配置语法
docker exec web-nginx nginx -s reload # 平滑重载
docker compose logs -f nginx # 查看日志
生产建议:Docker 内配置修改后先
nginx -t校验再reload,避免语法错误导致服务中断。日志务必挂载到宿主机,否则容器销毁后日志丢失。
2.5 验证安装
nginx -v # 查看版本
curl -I http://localhost # 请求头验证,应返回 200
看到 HTTP/1.1 200 OK 即部署成功。
三、配置结构拆解
Nginx 核心配置文件位于 /etc/nginx/nginx.conf(源码编译版在 /usr/local/nginx/conf/nginx.conf)。配置采用类 C 语言的块级结构:
# ============ 1. 全局块 ============
user nginx;
worker_processes auto; # 自动匹配 CPU 核心数
error_log /var/log/nginx/error.log warn;
pid /var/run/nginx.pid;
# ============ 2. Events 块 ============
events {
worker_connections 1024; # 单 Worker 最大连接数
use epoll; # 事件模型(Linux 默认 epoll)
}
# ============ 3. HTTP 块 ============
http {
include /etc/nginx/mime.types;
default_type application/octet-stream;
# 日志格式定义
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;
sendfile on;
keepalive_timeout 65;
# ============ 4. Server 块(虚拟主机) ============
server {
listen 80;
server_name example.com www.example.com;
# ============ 5. Location 块(路由匹配) ============
location / {
root /usr/share/nginx/html;
index index.html index.htm;
}
error_page 500 502 503 504 /5x.html;
location = /5x.html {
root /usr/share/nginx/html;
}
}
}
配置层级说明
| 块 | 作用 |
|---|---|
| 全局块 | 影响 Nginx 全局运行的指令:运行用户、Worker 进程数、PID 路径、全局错误日志 |
| Events 块 | 网络连接相关参数:单 Worker 最大连接数(worker_connections)、事件模型 |
| HTTP 块 | HTTP 协议全局指令:文件类型、日志格式、Gzip 压缩,可嵌套多个 server |
| Server 块 | 虚拟主机:一个 server 代表一个网站/服务,配置监听端口与域名 |
| Location 块 | 基于 URI 精确或正则匹配,定义请求处理逻辑(静态响应、代理转发、重定向) |
配置组织最佳实践
生产环境不要把大量 server 写进主配置文件,用 include 拆分管理:
# nginx.conf 的 http 块内
http {
include /etc/nginx/conf.d/*.conf; # 每个站点一个文件
include /etc/nginx/sites-enabled/*; # Debian 系习惯
}
/etc/nginx/
├── nginx.conf # 主配置
├── conf.d/
│ ├── static.conf # 静态资源站点
│ ├── api.conf # API 反向代理站点
│ └── blog.conf # 博客站点
└── mime.types
每个站点独立文件,
nginx -t可以精确定位是哪个文件语法出错,也便于团队协作与灰度上线。
四、核心应用场景与配置实战
4.1 静态资源服务器
Nginx 极其擅长处理静态文件(HTML、CSS、JS、图片等):
server {
listen 80;
server_name static.example.com;
# 静态资源根目录
location / {
root /data/www/static;
index index.html;
}
# 静态资源缓存控制(图片、字体、样式)
location ~* \.(jpg|jpeg|png|gif|ico|css|js|woff2)$ {
root /data/www/static;
expires 7d; # 浏览器缓存 7 天
add_header Cache-Control "public, no-transform";
}
}
4.2 正向代理 vs 反向代理
| 对比项 | 正向代理(Forward Proxy) | 反向代理(Reverse Proxy) |
|---|---|---|
| 代理对象 | 代理客户端 | 代理服务端 |
| 使用场景 | 内网上网、访问被限制的资源 | 负载均衡、网关、隐藏后端 |
| 客户端感知 | 客户端需配置代理 | 客户端无感知,只看到代理地址 |
| 服务端感知 | 服务端只知道代理 IP | 服务端直接接收请求 |
| 典型例子 | 公司上网代理、科学上网 | Nginx 转发到 Tomcat/Node.js |
4.3 反向代理配置
server {
listen 80;
server_name api.example.com;
location / {
proxy_pass http://127.0.0.1:8080; # 转发给后端的 Java/Node.js 服务
# 传递真实的客户端请求头
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_read_timeout 60s;
}
}
X-Forwarded-For对后端至关重要:后端通过它获取真实客户端 IP(做限流、审计、地域统计时必需),否则后端看到的全是 Nginx 的 IP。
4.4 负载均衡(Load Balancing)
通过 upstream 模块将请求分发到多台后端服务器,实现高可用与横向扩展:
# 定义后端服务器集群
upstream backend_cluster {
# 负载均衡策略(选一种):
# 1. 轮询 Round Robin(默认,无需声明)
# 2. 加权轮询:server 后加 weight=N
# 3. IP Hash:ip_hash,实现 Session 保持
# 4. 最少连接:least_conn
ip_hash;
server 192.168.1.10:8080 weight=3 max_fails=3 fail_timeout=30s;
server 192.168.1.11:8080 weight=1;
server 192.168.1.12:8080 backup; # 备用服务器,其他全挂时才启用
server 192.168.1.13:8080 down; # 手动下线维护
}
server {
listen 80;
server_name app.example.com;
location / {
proxy_pass http://backend_cluster;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
}
}
负载均衡策略对比
| 策略 | 配置方式 | 适用场景 | 说明 |
|---|---|---|---|
| 轮询 | 默认 | 服务器配置相近 | 逐个轮流分发 |
| 加权轮询 | weight=N | 服务器配置不同 | 高配机器分更多流量 |
| IP Hash | ip_hash | 需要 Session 保持 | 同一 IP 固定到同一台后端 |
| 最少连接 | least_conn | 长连接/请求耗时差异大 | 分给当前连接数最少的后端 |
注意:
ip_hash与weight可以同时使用,权重在 hash 分组内仍生效。Session 保持的现代替代方案是后端 Redis 共享 Session 或 JWT,不依赖 IP 绑定,更推荐。
4.5 HTTPS(SSL/TLS)配置
server {
listen 443 ssl;
http2 on; # Nginx 1.25.1+ 写法
server_name example.com;
ssl_certificate /etc/nginx/certs/example.com.crt;
ssl_certificate_key /etc/nginx/certs/example.com.key;
# SSL 协议与套件优化
ssl_protocols TLSv1.2 TLSv1.3;
ssl_ciphers HIGH:!aNULL:!MD5;
ssl_prefer_server_ciphers on;
# Session 缓存,减少 TLS 握手开销
ssl_session_cache shared:SSL:10m;
ssl_session_timeout 10m;
location / {
root /usr/share/nginx/html;
index index.html;
}
}
# 强制 HTTP 自动跳转 HTTPS
server {
listen 80;
server_name example.com;
return 301 https://$host$request_uri;
}
证书申请推荐 Let's Encrypt + certbot,自动签发与续期,无需手动操作证书过期问题。
4.6 WebSocket 代理
WebSocket 需要通过 HTTP Upgrade 机制升级协议,反向代理必须转发这两个头,否则连接失败:
server {
listen 80;
server_name ws.example.com;
location / {
proxy_pass http://127.0.0.1:9501; # 如 Swoole / Node.js WebSocket 服务
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade; # 协议升级
proxy_set_header Connection "upgrade"; # 保持长连接
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_read_timeout 3600s; # 长连接读超时调大
}
}
这组配置用于聊天、实时通知、在线协作等场景,是前端与后端实时通信的标配。
五、Location 匹配规则深入理解
Location 是 Nginx 路由匹配的核心,语法为:
location [ = | ~ | ~* | ^~ ] uri { ... }
匹配符优先级
| 匹配符 | 含义 | 优先级 |
|---|---|---|
= | 精确匹配(Exact Match) | 最高(1) |
^~ | 带前缀的普通匹配(匹配后不再检查正则) | 第二(2) |
~ | 区分大小写的正则表达式匹配 | 第三(3) |
~* | 不区分大小写的正则表达式匹配 | 第三(3) |
| 无 | 普通前缀匹配(如 /、/images/) | 最低(4) |
匹配流程
匹配规则示例
location = / {
# 仅匹配请求 http://example.com/(首页精确匹配)
}
location ^~ /static/ {
# 匹配任何以 /static/ 开头的路径,命中后停止向下正则匹配
# 静态资源用这个,避免被下面图片正则二次匹配
}
location ~* \.(gif|jpg|jpeg|png|css|js)$ {
# 匹配所有图片、样式、脚本结尾的请求(不区分大小写)
}
location / {
# 通配匹配,所有请求兜底
}
实战经验:静态资源用
^~,动态接口用~/~*,兜底用/。优先级记不住没关系,记住nginx -T可以查看最终合并后的完整配置,实际验证匹配结果最靠谱。
六、SPA 部署与前后端分离(前端开发者必看)
6.1 SPA History 路由回退
Vue / React 使用 History 模式路由时,刷新 /detail/123 这类路径,Nginx 找不到对应文件会返回 404。必须用 try_files 回退到 index.html:
server {
listen 80;
server_name myapp.example.com;
root /data/www/myapp;
index index.html;
location / {
try_files $uri $uri/ /index.html; # 找不到就回退到 index.html
}
# 静态资源带缓存(配合打包后的 hash 文件名)
location /assets/ {
expires 30d;
add_header Cache-Control "public, immutable";
}
}
6.2 前后端分离双 location 分流
一个域名同时承载前端静态资源和后端 API:
server {
listen 80;
server_name shop.example.com;
root /data/www/shop-front;
index index.html;
# 前端页面:history 路由回退
location / {
try_files $uri $uri/ /index.html;
}
# API 请求:代理到后端
location /api/ {
proxy_pass http://127.0.0.1:8080;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}
# 上传文件路径:代理到后端
location /upload/ {
proxy_pass http://127.0.0.1:8080;
client_max_body_size 50m; # 上传大小限制
}
}
6.3 完整上线流程(Vue 项目为例)
# 本地打包
npm run build
# 上传(示例:scp 到服务器)
scp -r dist/* user@server:/data/www/myapp/
# 服务器上校验并重载
nginx -t && nginx -s reload
七、安全加固
7.1 隐藏版本号
http {
server_tokens off; # 响应头不再暴露 Nginx 版本号
}
7.2 安全响应头
server {
# 防点击劫持(禁止 iframe 嵌套)
add_header X-Frame-Options "SAMEORIGIN" always;
# 防 MIME 类型嗅探
add_header X-Content-Type-Options "nosniff" always;
# 强制 HTTPS(HSTS,仅在 HTTPS 站点配置)
add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;
# 防止信息泄露(引荐来源控制)
add_header Referrer-Policy "strict-origin-when-cross-origin" always;
}
7.3 防盗链
防止其他网站直接引用你的图片/视频资源:
location ~* \.(gif|jpg|jpeg|png|webp|mp4)$ {
valid_referers none blocked server_names *.example.com;
if ($invalid_referer) {
return 403;
}
}
说明:
none允许直接访问(如浏览器地址栏输入),blocked允许无 referer 的请求,server_names只允许本站域名。
7.4 目录安全与上传限制
server {
# 关闭目录浏览,防止暴露目录结构
autoindex off;
# 上传大小限制(默认 1m,过小会导致 413)
client_max_body_size 20m;
}
7.5 基本认证(敏感目录加密码)
# 生成密码文件(需要 apache2-utils / httpd-tools)
htpasswd -c /etc/nginx/.htpasswd admin
location /admin/ {
auth_basic "Restricted Area";
auth_basic_user_file /etc/nginx/.htpasswd;
proxy_pass http://127.0.0.1:8080;
}
7.6 请求限流(防刷/防 DDoS)
limit_req 限制请求频率,limit_conn 限制并发连接数,两者常组合使用:
# HTTP 块内定义限流规则
limit_req_zone $binary_remote_addr zone=req_limit:10m rate=10r/s;
limit_conn_zone $binary_remote_addr zone=conn_limit:10m;
server {
location /api/ {
# 每秒最多 10 个请求,允许突发 20 个
limit_req zone=req_limit burst=20 nodelay;
# 同一 IP 最多 20 个并发连接
limit_conn conn_limit 20;
proxy_pass http://backend_cluster;
}
}
| 指令 | 作用 | 说明 |
|---|---|---|
limit_req_zone | 定义请求速率限制区 | rate=10r/s 表示每秒 10 请求 |
limit_req | 应用速率限制 | burst 允许突发量,nodelay 突发不排队 |
limit_conn_zone | 定义连接数限制区 | 按 IP 维度统计 |
limit_conn | 应用连接数限制 | 单 IP 最大并发 |
八、性能调优
8.1 Gzip 压缩
http {
gzip on;
gzip_min_length 1k; # 小于 1KB 不压缩
gzip_buffers 4 16k;
gzip_http_version 1.1;
gzip_comp_level 5; # 推荐 4-6,过高增加 CPU
gzip_types text/plain text/css application/json
application/javascript text/xml application/xml
application/xml+rss text/javascript image/svg+xml;
gzip_vary on;
}
8.2 高效文件传输
http {
sendfile on; # 开启零拷贝(Zero-Copy)
tcp_nopush on; # 数据包合并发送,配合 sendfile 使用
tcp_nodelay on; # 禁用 Nagle 算法,小包高频场景更实时
keepalive_timeout 65; # 长连接超时
}
8.3 反向代理缓存(proxy_cache)
后端接口响应做缓存,能显著降低后端压力(适用于变化不频繁的数据):
http {
# 缓存目录与共享内存定义
proxy_cache_path /data/nginx/cache levels=1:2 keys_zone=api_cache:10m
max_size=1g inactive=60m;
}
server {
location /api/ {
proxy_cache api_cache; # 启用缓存区
proxy_cache_key "$scheme$request_method$host$request_uri";
proxy_cache_valid 200 60m; # 200 响应缓存 60 分钟
proxy_cache_valid 404 1m;
proxy_cache_use_stale error timeout http_500 http_502 http_503; # 后端挂了用旧缓存
proxy_pass http://backend_cluster;
}
}
proxy_cache_use_stale是亮点:后端宕机时自动降级用旧缓存响应,避免用户直接看到 502。动态接口慎用缓存,可用Cache-Control头控制粒度。
8.4 静态文件缓存(open_file_cache)
缓存文件句柄、大小、修改时间,减少磁盘 IO:
http {
open_file_cache max=1000 inactive=20s; # 最多缓存 1000 个文件,20s 无访问淘汰
open_file_cache_valid 30s;
open_file_cache_min_uses 2; # 访问 2 次以上才缓存
open_file_cache_errors on;
}
8.5 内核参数与文件描述符
# nginx.conf 全局块
worker_processes auto;
worker_rlimit_nofile 65535; # 单 Worker 可打开的文件描述符上限
# /etc/sysctl.conf 内核参数调优
net.core.somaxconn = 65535 # 半连接队列长度
net.ipv4.ip_local_port_range = 1024 65535 # 本地端口范围
fs.file-max = 2097152 # 系统级文件描述符上限
生效:sudo sysctl -p
连接数估算公式
最大并发连接数 ≈ worker_processes × worker_connections
- 4 核 CPU、
worker_connections 1024→ 约 4096 并发。 - 反向代理场景每个连接占用 2 个连接(客户端 + 后端),实际并发约为一半,按需调大。
8.6 Brotli 与 HTTP/3(进阶)
- Brotli:比 Gzip 压缩率更高,需要第三方模块
ngx_brotli(源码编译时集成)。 - HTTP/3(QUIC):基于 UDP,减少连接建立延迟,需要
--with-http_v3_module编译参数与证书支持,适合对首屏速度极致追求的场景。
九、监控与日志分析
9.1 stub_status 状态监控
Nginx 内置状态页(需 --with-http_stub_status_module,包安装默认开启):
server {
listen 80;
server_name monitor.example.com;
location /nginx_status {
stub_status on;
access_log off; # 状态页不记访问日志
allow 127.0.0.1; # 只允许本机访问
allow 192.168.1.0/24; # 或内网网段
deny all;
}
}
访问输出示例:
Active connections: 291
server accepts handled requests
16630948 16630948 31070465
Reading: 6 Writing: 179 Waiting: 106
| 指标 | 含义 |
|---|---|
| Active connections | 当前活跃连接数 |
| accepts / handled | 接受的连接 / 处理的连接(相等说明没有丢弃) |
| requests | 累计请求数 |
| Reading / Writing | 正在读/写请求头的连接数 |
| Waiting | 空闲长连接数 |
9.2 慢请求定位
在 log_format 中增加耗时字段:
log_format slow '$remote_addr - $request_time - $upstream_response_time - "$request" - $status';
# 筛选响应超过 3 秒的请求
awk '$2 > 3' /var/log/nginx/access.log | head -20
$request_time是完整请求耗时(含网络),$upstream_response_time是后端处理耗时。两者差距大说明瓶颈在网络/排队,接近则瓶颈在后端程序。
9.3 日志切割(logrotate)
防止日志无限增长占满磁盘,创建 /etc/logrotate.d/nginx:
/var/log/nginx/*.log {
daily # 每天切割
missingok
rotate 14 # 保留 14 份
compress # 压缩旧日志
delaycompress
notifempty # 空日志不处理
sharedscripts
postrotate
[ -f /var/run/nginx.pid ] && kill -USR1 `cat /var/run/nginx.pid`
endscript
}
kill -USR1通知 Nginx 重新打开日志文件,这是 Nginx 优雅切日志的标准信号。
9.4 日志分析常用命令
# Top10 访问 IP
awk '{print $1}' /var/log/nginx/access.log | sort | uniq -c | sort -rn | head -10
# Top10 请求路径
awk '{print $7}' /var/log/nginx/access.log | sort | uniq -c | sort -rn | head -10
# 状态码分布
awk '{print $9}' /var/log/nginx/access.log | sort | uniq -c | sort -rn
# 5xx 错误请求
grep ' 5[0-9][0-9] ' /var/log/nginx/access.log | tail -20
十、常用命令与排错
10.1 常用控制命令
nginx -t # 检查配置文件语法
nginx -s reload # 优雅重载配置(平滑,不中断服务)
nginx -s stop # 快速停止
nginx -s quit # 平滑停止(处理完当前请求)
nginx -v # 版本
nginx -V # 详细编译参数及模块信息
systemctl reload nginx # systemd 方式重载
10.2 常见错误码详解
| 错误码 | 含义 | 排查方向 |
|---|---|---|
| 400 | 请求头过大 | 调大 large_client_header_buffers 4 32k |
| 403 | 权限不足 | 目录权限、缺少 index 文件、autoindex off |
| 404 | 资源不存在 | 静态路径、SPA 未配 try_files、location 匹配错误 |
| 413 | 请求体过大 | 调大 client_max_body_size |
| 499 | 客户端主动断开 | 客户端超时/取消,常见于长耗时接口 |
| 500 | 后端程序异常 | 查后端应用日志 |
| 502 | 连接后端失败 | 后端服务挂了/端口未监听/防火墙拦截 |
| 503 | 服务不可用 | 限流触发 / Worker 过载 |
| 504 | 后端响应超时 | 调大 proxy_read_timeout,或后端有性能瓶颈 |
10.3 502 / 504 排查链路
10.4 压测验证
# ab 压测:1 万请求,100 并发
ab -n 10000 -c 100 http://localhost/
# wrk(更现代,支持多线程)
wrk -t4 -c100 -d30s http://localhost/
重点关注指标:Requests per second(QPS)、Time per request、Failed requests(应为 0)。
十一、进阶:灰度发布与 OpenResty
11.1 灰度发布
利用 upstream 权重动态调整,实现平滑上线:
# 阶段一:新版本 10% 流量
upstream backend {
server 192.168.1.10:8080 weight=9; # 旧版本
server 192.168.1.20:8080 weight=1; # 新版本
}
# 阶段二:观察无误后全量切换
upstream backend {
server 192.168.1.10:8080 down; # 旧版本下线
server 192.168.1.20:8080 weight=10;
}
nginx -t && nginx -s reload # 修改权重后平滑生效,无需重启
11.2 健康检查
开源版 Nginx 通过 max_fails 与 fail_timeout 做被动健康检查(请求失败才标记):
upstream backend {
server 192.168.1.10:8080 max_fails=3 fail_timeout=30s;
# 连续失败 3 次,30 秒内不再分发请求给它
}
需要主动健康检查(定时探测后端)时,使用 OpenResty 或 Nginx Plus 商业版。
11.3 OpenResty / Lua 生态
OpenResty 是 Nginx + LuaJIT 的增强发行版,可在 Nginx 请求处理阶段嵌入 Lua 脚本:
| 能力 | 说明 |
|---|---|
| 动态限流/熔断 | 按业务维度(用户、商品)定制限流 |
| API 网关 | 鉴权、签名校验、流量染色、灰度路由 |
| 动态配置 | 不 reload 即可改 upstream、路由规则 |
| 缓存聚合 | 缓存穿透保护、接口聚合 |
一句话:Nginx 是"静态配置的网关",OpenResty 是"可编程的网关"。业务复杂度上来后,网关逻辑必然要动态化。
总结
Nginx 凭借高效的事件驱动与异步非阻塞架构,成为现代 Web 架构中的核心基础设施。本文完整覆盖了从安装到生产上线的全链路:
| 阶段 | 核心内容 |
|---|---|
| 架构理解 | Master-Worker + Epoll,理解它为什么快 |
| 安装部署 | 包管理 / 源码 / Docker,生产推荐 Docker 或包管理 |
| 配置基础 | 五大块结构 + include 拆分管理 |
| 核心场景 | 静态资源、正反向代理、负载均衡、HTTPS、WebSocket |
| 路由核心 | Location 匹配优先级与匹配流程 |
| 前端实战 | SPA history 回退、前后端分离、上线流程 |
| 安全加固 | 响应头、防盗链、限流、认证、上传限制 |
| 性能优化 | Gzip、零拷贝、proxy_cache、内核参数 |
| 监控排错 | stub_status、慢日志、日志切割、错误码链路 |
| 进阶方向 | 灰度发布、主动健康检查、OpenResty 网关 |
给新手的建议路线:先用 Docker 起一个 Nginx → 配一个静态站点 → 加反向代理接上自己的后端 → 配 HTTPS → 然后逐步补充安全头、缓存、限流。不要一上来就背配置,先跑起来,再逐个场景理解——Nginx 的每个配置指令都有明确的使用场景,用到时查文档记忆最牢固。
Nginx 适合高并发静态与反向代理场景,业务网关逻辑复杂时叠加 OpenResty,微服务架构下配合注册中心做动态发现。理解原理、按场景选型、动手验证,才是掌握 Nginx 的正确路径。