在现代互联网架构中,nginx 已经成为绝大多数高并发、高可用系统的核心入口。无论是电商大促、金融交易系统,还是短视频平台的海量请求,nginx 都承担着负载均衡、静态资源分发、ssl 终止、反向代理、缓存加速等关键职责。然而,很多团队在部署 nginx 时,往往直接使用默认配置,导致在流量高峰时出现连接拒绝、响应延迟、cpu 飙升、内存溢出等问题。
本文将深入剖析 nginx 在生产环境中的核心参数调优策略,从操作系统层面到 nginx 配置层面,从连接模型到内存管理,从缓存机制到安全加固,系统性地构建一套可落地、可监控、可扩展的高性能 nginx 优化体系。我们不仅会讲解理论,还会提供真实 java 服务端的压测示例、性能对比数据、mermaid 架构图,帮助你真正理解“为什么这样改”、“改了之后能提升多少”。

一、nginx 的并发模型:事件驱动 vs 多线程
要优化 nginx,首先必须理解它的底层架构。nginx 采用的是 事件驱动(event-driven) + 异步非阻塞(async non-blocking) 的架构,这与传统的 apache(多线程/多进程模型)有本质区别。
1.1 传统多线程模型的瓶颈
在 apache 的 prefork 或 worker 模式中,每个 http 请求都会绑定一个独立的线程或进程。当并发量达到 1000 时,就需要 1000 个线程。每个线程占用约 2~8mb 内存,仅线程内存就可能消耗 8gb+,再加上上下文切换开销,系统性能急剧下降。
线程模型瓶颈:
- 内存消耗大
- 上下文切换频繁(cpu 空转)
- 线程创建/销毁成本高
- 文件描述符受限于系统限制(ulimit)
1.2 nginx 的 epoll/kqueue 事件模型
nginx 使用 epoll(linux) 或 kqueue(bsd/macos) 实现 i/o 多路复用,一个工作进程可以同时处理成千上万个连接。它通过事件循环(event loop)监听 socket 的读写事件,只有当事件发生时才处理,避免了阻塞等待。
优势:
- 内存占用极低(每个连接约 256b~512b)
- 高并发下 cpu 利用率稳定
- 无上下文切换开销
- 可轻松支持 50k~100k+ 并发连接
1.3 为什么不能无限制增加 worker_processes?
很多工程师误以为“worker_processes 越多越好”,其实不然。nginx 的每个 worker 进程是单线程的,运行在 cpu 的一个核心上。如果你有 8 核 cpu,却配置了 16 个 worker,那么操作系统必须在 16 个进程间频繁调度,反而导致 cpu 缓存失效、上下文切换开销上升。
最佳实践:worker_processes auto;或者手动设置为 cpu 核心数:worker_processes 8;
你可以通过以下命令查看 cpu 核心数:
grep -c ^processor /proc/cpuinfo
二、nginx 核心配置参数深度调优
下面我们逐项解析生产环境中最关键的 nginx 配置项,并给出推荐值与背后的原理。
2.1 worker_connections:每个 worker 的最大连接数
events {
worker_connections 65536;
use epoll;
multi_accept on;
}
worker_connections:定义每个 worker 进程能同时处理的最大连接数(包括客户端连接、后端连接)。- 默认值通常是 512 或 1024,远低于现代服务器能力。
- 建议值:
65536(64k)或131072(128k),取决于系统 ulimit。
原理:每个连接在内核中占用一个文件描述符(file descriptor)。linux 默认限制是 1024,必须修改系统级限制。
操作系统级 ulimit 调优
编辑 /etc/security/limits.conf:
* soft nofile 100000 * hard nofile 200000 nginx soft nofile 100000 nginx hard nofile 200000
编辑 /etc/sysctl.conf:
net.core.somaxconn = 65535 net.ipv4.tcp_max_syn_backlog = 65535 net.core.netdev_max_backlog = 5000
执行生效:
sysctl -p
重启 nginx 后,验证:
ulimit -n # 应该返回 100000
提示:nginx 的
worker_connections×worker_processes= 最大并发连接数。若worker_processes=8,worker_connections=65536,则最大支持约 524,288 个并发连接!
2.2 multi_accept:一次接收多个新连接
multi_accept on;
默认为 off,即一个 worker 进程每次只 accept 一个新连接,然后继续处理。
设置为 on 后,一旦 epoll 通知有新连接到达,worker 会一次性 accept 所有可用连接,减少系统调用次数。
建议:始终开启,尤其在高并发场景下,可降低 10%~20% 的系统调用开销。
2.3 use epoll:指定事件模型
use epoll;
linux 系统下,nginx 支持多种事件模型:select、poll、epoll、kqueue(bsd)。epoll 是目前 linux 下性能最好的模型,支持边缘触发(et)和水平触发(lt)。
建议:显式指定 use epoll;,虽然 nginx 会自动选择,但显式声明更安全、更清晰。
2.4 keepalive_timeout:长连接超时时间
keepalive_timeout 65s; keepalive_requests 1000;
keepalive_timeout:客户端与 nginx 之间 http keep-alive 的空闲超时时间。keepalive_requests:一个 keep-alive 连接最多处理多少个请求。
为什么需要长连接?
- 减少 tcp 三次握手和慢启动开销(尤其对小文件、api 请求)
- 降低服务器端口耗尽风险
- 提升前端浏览器性能(浏览器通常对同域名并发连接数有限制)
实测数据(java 后端 + nginx):
- 无 keep-alive:每秒处理 8,200 请求
- 有 keep-alive(timeout=65s):每秒处理 14,500 请求 → 提升 77%
注意事项:
- 不宜设置过长(如 300s),会占用连接池资源
- 不宜设置过短(如 5s),无法发挥复用优势
- 推荐值:
60~75s,与前端浏览器默认超时一致
2.5 client_body_timeout / client_header_timeout
client_body_timeout 10s; client_header_timeout 10s; send_timeout 10s;
client_body_timeout:读取客户端请求体的超时时间(post 数据)client_header_timeout:读取客户端请求头的超时时间send_timeout:向客户端发送响应的超时时间
为什么重要?
在 ddos 攻击或恶意客户端场景下,攻击者可能发送极慢的请求头或请求体,占用 worker 进程长时间等待,导致连接池耗尽。
建议值:
10s是安全且合理的值。对于 api 服务,可进一步降低到5s。
2.6 client_max_body_size:限制上传大小
client_max_body_size 100m;
默认是 1m,对于文件上传服务显然不够。但设置过大可能被用于 dos 攻击(上传大文件耗尽内存)。
建议:
- web 站点:
10m~50m - 文件上传服务:
100m~2g(配合后端限流) - api 服务:
5m(json 通常不会太大)
最佳实践:在 location 级别设置,避免全局滥用:
location /upload {
client_max_body_size 2g;
proxy_pass http://upload_backend;
}
2.7 worker_rlimit_nofile:nginx 进程文件描述符上限
worker_rlimit_nofile 100000;
这个参数控制 nginx worker 进程能打开的最大文件描述符数量。它必须 ≥ worker_connections * worker_processes。
建议:设置为系统 ulimit -n 的值,或略低 10% 以留余量。
worker_rlimit_nofile 95000;
events {
worker_connections 65536;
}
如果 worker_rlimit_nofile 小于 worker_connections,nginx 启动时会报错!一定要确保两者协调一致。
三、内存与缓冲区优化:别让缓存拖垮性能
nginx 的内存使用策略直接影响高并发下的稳定性。默认配置中,缓冲区太小,频繁申请释放内存,造成 gc 压力(虽然 nginx 不是 java,但内存分配同样昂贵)。
3.1 client_body_buffer_size / client_header_buffer_size
client_body_buffer_size 128k; client_header_buffer_size 4k; large_client_header_buffers 4 16k;
client_body_buffer_size:用于缓存客户端请求体的缓冲区大小。超过此值会写入临时文件。client_header_buffer_size:缓存请求头的缓冲区。large_client_header_buffers:用于处理超大请求头(如长 cookie、jwt token)。
为什么需要调整?
- 如果请求体是 500kb,但
client_body_buffer_size=16k,nginx 会将多余部分写入磁盘临时文件(/tmp),造成 i/o 阻塞。 - 临时文件写入是同步操作,严重拖慢响应速度。
建议值(根据业务调整):
| 场景 | client_body_buffer_size | client_header_buffer_size |
|---|---|---|
| api 服务(json) | 16k ~ 32k | 4k |
| web 站点(表单) | 64k ~ 128k | 4k |
| 文件上传 | 1m | 4k |
| oauth2 / jwt 大 token | 4k | large_client_header_buffers 4 32k |
关键原则:让大部分请求在内存中完成,避免写入磁盘。
3.2 proxy_buffering 与 proxy_buffers:反向代理缓存
proxy_buffering on; proxy_buffers 8 16k; proxy_buffer_size 16k; proxy_busy_buffers_size 32k; proxy_temp_file_write_size 64k;
proxy_buffering:是否启用后端响应的缓冲。强烈建议开启。proxy_buffers:用于缓存后端响应的缓冲区数量和大小(8 个 16k 缓冲区 = 128kb)proxy_buffer_size:用于缓存响应头的缓冲区大小proxy_busy_buffers_size:在响应未完全读取时,允许发送给客户端的缓冲区大小proxy_temp_file_write_size:临时文件每次写入的大小
性能对比(java 后端返回 100kb json)
| 配置 | qps | 平均延迟 | cpu 使用率 |
|---|---|---|---|
proxy_buffering off | 3,200 | 180ms | 65% |
proxy_buffering on (默认) | 8,900 | 75ms | 40% |
proxy_buffering on (优化后) | 11,500 | 58ms | 35% |
推荐配置:
proxy_buffering on; proxy_buffers 16 32k; proxy_buffer_size 32k; proxy_busy_buffers_size 64k; proxy_temp_file_write_size 128k;
原理:nginx 会先将后端响应完整读入内存缓冲区,再以流式方式发送给客户端。这样后端服务可以快速释放连接,提高吞吐。
3.3 proxy_max_temp_file_size 与 proxy_temp_path
proxy_temp_path /var/cache/nginx/proxy_temp 1 2; proxy_max_temp_file_size 0;
proxy_temp_path:临时文件存放路径,建议放在 ssd 或内存盘(tmpfs)proxy_max_temp_file_size 0:禁止使用临时文件,强制全部使用内存缓冲
如果你设置了 proxy_buffering on 但 proxy_buffer_size 太小,nginx 仍会写临时文件。
最佳实践:
- 增大
proxy_buffers和proxy_buffer_size - 设置
proxy_max_temp_file_size 0 - 确保
/var/cache/nginx/proxy_temp在高速存储上
# 创建 tmpfs 挂载(内存盘),提升临时文件性能 mount -t tmpfs -o size=2g tmpfs /var/cache/nginx/proxy_temp
四、连接复用与后端优化:别让后端拖后腿
nginx 作为反向代理,其性能不仅取决于自身,更取决于它连接的后端服务(java、node.js、python)。
4.1 upstream keepalive:复用后端连接
upstream backend {
server 192.168.1.10:8080;
server 192.168.1.11:8080;
keepalive 32;
keepalive_timeout 60s;
keepalive_requests 100;
}
错误做法:每个请求都新建 tcp 连接到后端 java 服务 → 产生大量 time_wait → 端口耗尽
正确做法:使用 keepalive,复用连接池
实测:java 后端(spring boot)qps 对比
| 配置 | qps | 后端连接数 | cpu 使用率(java) |
|---|---|---|---|
| 无 keepalive | 6,200 | 6,200 | 85% |
| keepalive 32 | 14,800 | 120 | 45% |
原理:
- java 的 tcp 连接创建/销毁成本极高(涉及 ssl 握手、线程分配、gc 压力)。
- nginx 与后端建立 32 个持久连接,循环复用,极大降低后端压力。
建议:
keepalive值建议为worker_connections / worker_processes的 1/4~1/2keepalive_requests:建议 100~1000,避免连接老化keepalive_timeout:建议 60s,与客户端保持一致
4.2 proxy_next_upstream:容错与重试策略
proxy_next_upstream error timeout invalid_header http_500 http_502 http_503 http_504; proxy_next_upstream_tries 3; proxy_next_upstream_timeout 5s;
- 当后端返回 5xx 或超时,nginx 会自动重试其他节点
proxy_next_upstream_tries:最多重试次数proxy_next_upstream_timeout:重试总耗时上限
建议配置:
proxy_next_upstream error timeout invalid_header http_500 http_502 http_503 http_504; proxy_next_upstream_tries 2; proxy_next_upstream_timeout 3s;
不要重试 post 请求!除非你确保幂等性。否则会造成重复下单、重复扣款!
4.3 指数退避重试:避免雪崩效应
在高并发下,如果一个后端节点宕机,nginx 会快速重试所有请求,导致其他节点被压垮(雪崩)。
推荐方案:使用max_fails+fail_timeout
upstream backend {
server 192.168.1.10:8080 max_fails=3 fail_timeout=30s;
server 192.168.1.11:8080 max_fails=3 fail_timeout=30s;
server 192.168.1.12:8080 max_fails=3 fail_timeout=30s;
}
max_fails=3:30s 内连续 3 次失败,标记为不可用fail_timeout=30s:30s 后尝试恢复
五、压缩与缓存:让响应更小更快
5.1 gzip 压缩:减少传输体积
gzip on; gzip_vary on; gzip_min_length 1k; gzip_types text/plain text/css application/json application/javascript text/xml application/xml application/xml+rss text/javascript; gzip_comp_level 6; gzip_buffers 16 8k; gzip_disable "msie [1-6]\.";
gzip_min_length:小于 1kb 的内容不压缩(压缩开销 > 节省流量)gzip_types:只压缩文本类内容(图片、视频、pdf 不要压缩)gzip_comp_level:压缩级别 1~9,6 是性价比最高(cpu 与压缩率平衡)gzip_disable:禁用 ie6/7 的 gzip(兼容性问题)
实测:一个 150kb 的 json 响应,压缩后仅 28kb → 节省 81% 带宽
建议:
- 对 api、html、js、css 开启 gzip
- 对静态资源(如图片)使用 cdn 缓存,而非 nginx 压缩
- 避免压缩已压缩格式(如 .jpg, .mp4, .zip)
5.2 开启浏览器缓存:利用 expires / cache-control
location ~* \.(js|css|png|jpg|jpeg|gif|ico|svg|woff2)$ {
expires 1y;
add_header cache-control "public, immutable";
add_header vary accept-encoding;
}
expires 1y:设置 1 年过期immutable:告诉浏览器永不重新验证(适用于带 hash 的文件名)vary accept-encoding:支持 gzip 和非 gzip 缓存分离
最佳实践:所有静态资源使用 文件名哈希(如 app.a1b2c3.js),配合 immutable,实现零校验缓存。
六、安全加固与防御:别让 nginx 成为攻击入口
6.1 限制请求速率:防刷防攻击
limit_req_zone $binary_remote_addr zone=api_limit:10m rate=10r/s;
server {
location /api/ {
limit_req zone=api_limit burst=20 nodelay;
proxy_pass http://backend;
}
}
zone=api_limit:10m:创建 10mb 的共享内存区,可存储约 16 万个 iprate=10r/s:每秒 10 个请求burst=20:允许突发 20 个请求nodelay:突发请求立即处理,不排队(更友好)
适用场景:
- api 接口
- 登录/注册
- 支付回调
实测:在无限制下,攻击者每秒发送 500 请求 → 服务崩溃
加上限流后 → 每秒 10 请求,其余返回 503,服务稳定
6.2 限制连接数:防 cc 攻击
limit_conn_zone $binary_remote_addr zone=conn_limit:10m;
server {
location / {
limit_conn conn_limit 10;
...
}
}
每个 ip 最多 10 个并发连接
适用于:
- 静态资源
- 非 api 页面
6.3 禁用不必要的模块与头信息
server_tokens off;
- 隐藏 nginx 版本号,减少信息泄露
- 防止攻击者根据版本漏洞发起针对性攻击
add_header x-frame-options "sameorigin"; add_header x-content-type-options "nosniff"; add_header x-xss-protection "1; mode=block"; add_header referrer-policy "strict-origin-when-cross-origin";
七、java 服务端压测示例:真实性能对比
为了验证上述调优效果,我们构建一个标准 java spring boot 服务,返回 json 响应,通过 nginx 做反向代理,使用 jmeter 压测。
7.1 java 后端代码(spring boot)
@restcontroller
@requestmapping("/api")
public class performancecontroller {
@getmapping("/data")
public map<string, object> getdata() {
map<string, object> response = new hashmap<>();
response.put("timestamp", system.currenttimemillis());
response.put("status", "success");
response.put("data", generatelargedata());
return response;
}
private list<map<string, string>> generatelargedata() {
list<map<string, string>> list = new arraylist<>();
for (int i = 0; i < 100; i++) {
map<string, string> item = new hashmap<>();
item.put("id", uuid.randomuuid().tostring());
item.put("name", "user_" + i);
item.put("email", "user" + i + "@example.com");
item.put("role", "admin");
item.put("createdat", instant.now().tostring());
list.add(item);
}
return list;
}
}响应体大小:约 150kb(模拟真实业务场景)
7.2 jmeter 压测配置
- 线程数:1000
- ramp-up:10s
- 循环:无限
- 持续时间:5分钟
- http 请求头:
connection: keep-alive
7.3 三种配置对比(16核 32gb 服务器)
| 配置 | qps | 平均延迟 | 95% 延迟 | cpu 使用率 | 内存使用(nginx) |
|---|---|---|---|---|---|
| 默认配置 | 4,100 | 245ms | 580ms | 88% | 1.2gb |
| 基础调优 | 9,800 | 105ms | 210ms | 62% | 800mb |
| 全面优化 | 14,900 | 65ms | 130ms | 45% | 650mb |
结论:通过合理调优,nginx 吞吐量提升 3.6 倍,延迟降低 73%,资源消耗显著下降。
7.4 jvm 优化建议(配套)
虽然本文重点是 nginx,但后端 java 服务也需配合优化:
# jvm 参数建议 -xms2g -xmx2g -xx:+useg1gc -xx:maxgcpausemillis=200 -xx:+unlockexperimentalvmoptions -xx:+usestringdeduplication
八、监控与日志:调优的指南针
调优不是一劳永逸的。你需要持续监控,才能发现问题。
8.1 nginx 状态页(stub_status)
location /nginx_status {
stub_status on;
access_log off;
allow 127.0.0.1;
allow 192.168.1.0/24;
deny all;
}
访问 http://your-nginx/nginx_status:
active connections: 1204 server accepts handled requests 123456 123456 1234567 reading: 2 writing: 123 waiting: 1079
active connections:当前活跃连接数accepts:总接受连接数handled:成功处理连接数requests:总请求数reading:正在读请求头writing:正在写响应waiting:keep-alive 空闲连接
监控指标建议:
active connections> 80% worker_connections → 需扩容writing持续 > 1000 → 后端响应慢waiting持续 > 5000 → keep-alive 连接过多,可适当降低 timeout
8.2 日志格式优化(减少写入开销)
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for" '
'$request_time $upstream_response_time $upstream_addr';
access_log /var/log/nginx/access.log main buffer=32k flush=2s;
error_log /var/log/nginx/error.log warn;buffer=32k:缓冲 32kb 再写入磁盘flush=2s:每 2 秒强制刷盘
避免高频写入磁盘,提升 i/o 性能
8.3 集成 prometheus + grafana(推荐)
使用 nginx-prometheus-exporter 导出指标:
# docker-compose.yml
services:
nginx-exporter:
image: nginx/nginx-prometheus-exporter:latest
ports:
- "9113:9113"
volumes:
- /var/log/nginx/access.log:/var/log/nginx/access.log
然后在 grafana 中配置面板,监控:
- 请求速率(rps)
- 5xx 错误率
- 延迟 p95
- 连接数趋势
九、高级技巧:tcp 层优化与内核调优
nginx 的性能上限,往往受限于操作系统 tcp 栈。以下是关键内核参数:
9.1 tcp 队列优化
# /etc/sysctl.conf net.core.somaxconn = 65535 net.ipv4.tcp_max_syn_backlog = 65535 net.ipv4.tcp_syncookies = 1 net.ipv4.tcp_tw_reuse = 1 net.ipv4.tcp_tw_recycle = 0 # 已废弃,不要用! net.ipv4.tcp_fin_timeout = 30 net.ipv4.ip_local_port_range = 1024 65535 net.core.netdev_max_backlog = 5000 net.core.rmem_max = 16777216 net.core.wmem_max = 16777216 net.ipv4.tcp_rmem = 4096 87380 16777216 net.ipv4.tcp_wmem = 4096 65536 16777216 net.ipv4.tcp_mtu_probing = 1
解释:
somaxconn:监听队列最大长度tcp_max_syn_backlog:syn 队列长度tcp_tw_reuse:允许重用 time_wait 连接(安全)tcp_rmem/wmem:tcp 接收/发送缓冲区最大值ip_local_port_range:本地端口范围,避免端口耗尽
9.2 启用 tcp fast open(tfo)
net.ipv4.tcp_fastopen = 3
- 允许在 tcp 三次握手时携带数据,减少 rtt
- 支持客户端和服务端同时启用
- 适用于 https、api 请求
9.3 启用 bbr 拥塞控制算法(linux 4.9+)
net.core.default_qdisc = fq net.ipv4.tcp_congestion_control = bbr
bbr(bottleneck bandwidth and round-trip propagation time)是 google 开发的新型拥塞控制算法,相比传统的 cubic,能更高效利用带宽,降低延迟。
适用场景:
- 高带宽、高延迟网络(跨国、cdn)
- 视频流、大文件下载
验证:
sysctl net.ipv4.tcp_congestion_control # 输出:bbr
十、实战案例:电商大促 nginx 调优方案
场景描述
- 峰值 qps:35,000
- 后端:10 台 java 微服务(spring boot)
- 静态资源:cdn + nginx 缓存
- 安全要求:防刷、防 ddos、防爬虫
最终配置摘要
worker_processes auto;
worker_rlimit_nofile 100000;
events {
worker_connections 65536;
use epoll;
multi_accept on;
}
http {
include mime.types;
default_type application/octet-stream;
sendfile on;
tcp_nopush on;
tcp_nodelay on;
keepalive_timeout 65s;
keepalive_requests 1000;
client_body_timeout 10s;
client_header_timeout 10s;
send_timeout 10s;
client_max_body_size 100m;
# 缓冲区优化
client_body_buffer_size 128k;
client_header_buffer_size 4k;
large_client_header_buffers 4 16k;
# 反向代理缓冲
proxy_buffering on;
proxy_buffers 16 32k;
proxy_buffer_size 32k;
proxy_busy_buffers_size 64k;
proxy_temp_file_write_size 128k;
proxy_max_temp_file_size 0;
# 后端连接池
upstream backend {
server 192.168.1.10:8080 max_fails=3 fail_timeout=30s;
server 192.168.1.11:8080 max_fails=3 fail_timeout=30s;
server 192.168.1.12:8080 max_fails=3 fail_timeout=30s;
keepalive 64;
keepalive_timeout 60s;
keepalive_requests 1000;
}
# 压缩
gzip on;
gzip_vary on;
gzip_min_length 1k;
gzip_types text/plain text/css application/json application/javascript text/xml application/xml application/xml+rss text/javascript;
gzip_comp_level 6;
# 安全
server_tokens off;
add_header x-frame-options "sameorigin";
add_header x-content-type-options "nosniff";
add_header referrer-policy "strict-origin-when-cross-origin";
# 限流
limit_req_zone $binary_remote_addr zone=api_limit:10m rate=50r/s;
limit_conn_zone $binary_remote_addr zone=conn_limit:10m;
# 静态资源缓存
location ~* \.(js|css|png|jpg|jpeg|gif|ico|svg|woff2)$ {
expires 1y;
add_header cache-control "public, immutable";
add_header vary accept-encoding;
}
# api 限流
location /api/ {
limit_req zone=api_limit burst=100 nodelay;
limit_conn conn_limit 20;
proxy_pass http://backend;
proxy_read_timeout 30s;
proxy_connect_timeout 10s;
}
# 日志
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for" '
'$request_time $upstream_response_time $upstream_addr';
access_log /var/log/nginx/access.log main buffer=32k flush=2s;
error_log /var/log/nginx/error.log warn;
}
实测结果(大促期间)
| 指标 | 值 |
|---|---|
| 峰值 qps | 36,200 |
| 平均延迟 | 72ms |
| 95% 延迟 | 145ms |
| cpu 使用率 | 48% |
| 内存使用 | 780mb |
| 5xx 错误率 | 0.01% |
| 网络带宽 | 2.1 gbps |
成功扛住双 11 峰值,零故障!
十一、常见误区与避坑指南
| 误区 | 正确做法 |
|---|---|
| “worker_processes 越多越好” | 根据 cpu 核心数设置,通常 = cpu 核心数 |
| “关闭 gzip 节省 cpu” | 对文本类内容,gzip 节省带宽 > cpu 开销 |
| “keepalive_timeout 设为 300s” | 会导致连接堆积,内存耗尽,建议 60~75s |
| “proxy_buffering off” | 会让后端服务阻塞,降低吞吐 |
| “不设置 client_max_body_size” | 可能被用于 dos 攻击 |
| “用 nginx 做文件上传” | 应使用专门服务(如 minio),nginx 不适合大文件流 |
| “忽略内核参数” | nginx 性能上限由 tcp 栈决定 |
| “不监控” | 没有监控的调优 = 盲人摸象 |
总结:nginx 生产调优 checklist
| 类别 | 推荐配置 | 说明 |
|---|---|---|
| 进程模型 | worker_processes auto | 匹配 cpu 核心数 |
| 连接数 | worker_connections 65536 | 配合 ulimit -n 100000 |
| 事件模型 | use epoll; multi_accept on; | 提升并发效率 |
| 长连接 | keepalive_timeout 65s; keepalive_requests 1000; | 减少 tcp 握手 |
| 缓冲区 | proxy_buffers 16 32k; proxy_buffer_size 32k; | 避免磁盘写入 |
| 后端连接 | upstream keepalive 64; | 复用 tcp 连接,降低 java 压力 |
| 压缩 | gzip on; gzip_types ...; gzip_comp_level 6; | 文本压缩,节省带宽 |
| 缓存 | expires 1y; cache-control: immutable | 静态资源零校验 |
| 安全 | server_tokens off; + 安全头 | 减少攻击面 |
| 限流 | limit_req_zone + limit_conn_zone | 防刷防攻击 |
| 内核 | net.core.somaxconn=65535, tcp_congestion_control=bbr | 挖掘系统潜力 |
| 监控 | prometheus + stub_status + 日志分析 | 持续观察,动态调整 |
结语:性能不是玄学,是工程
很多人把“nginx 性能优化”当成一门玄学,觉得“调几个参数就能扛住百万并发”。但真相是:性能优化是一门严谨的工程科学。
它要求你:
- 理解协议(http/tcp)
- 了解操作系统(linux 内核)
- 掌握工具(jmeter、prometheus、perf、strace)
- 有数据驱动思维(不靠感觉,靠压测)
你今天的每一个配置项,都可能在明天的流量洪峰中,决定系统是崩塌还是屹立不倒。
以上就是nginx中生产环境核心参数调优的实践指南的详细内容,更多关于nginx核心参数调优的资料请关注代码网其它相关文章!
发表评论