nginx 开启 HTTP/2 之后的几个小坑
2026-09-12
把几台机器上的站点都加上 h2 之后踩了几个坑,记下来。
1. 写法变了
老写法是 listen 443 ssl http2;,从 1.25.1 开始 http2 这个参数被废弃,改用独立的指令,否则会有 warning:
server {
listen 443 ssl;
http2 on;
server_name example.com;
}
2. HTTP/2 下 keepalive 的收益变低了
h2 是多路复用,一条连接上并发多个流,所以 upstream 的 keepalive 主要影响的是复用连接池,而不是并发能力。之前为了压测调的 keepalive_requests 基本可以回退到默认值。
3. gRPC 和普通站点混跑
gRPC 走 h2 的 trailer,用 grpc_pass 就够了。如果是同一端口既跑网页又跑 gRPC,最省事的还是按 location 或 Host 分开:
location /grpc.Service/ {
grpc_pass grpc://127.0.0.1:9090;
}
location / {
proxy_pass http://127.0.0.1:8080;
}
4. h2 不能和 ssl_prefer_server_ciphers 之类的老参数硬凑
其实不会报错,只是没意义——h2 的 cipher 套件由 TLS 1.3 决定,老的那套 ssl_ciphers 列表只对 1.2 生效。留着当兼容没问题,但如果只开 1.3 就可以删掉。
5. 真的变快了吗
对小站来说,首屏提升主要来自多了几路并行请求。如果是单文件下载,h2 甚至可能因为窗口和优先级的原因略慢一点。所以别指望它包治百病。