Nginx 反向代理使用教程
1. Nginx 反向代理是什么
反向代理可以理解为:用户访问域名时,先到 Nginx,Nginx 再把请求转发给服务器内部真正运行的应用。
例如应用运行在:
1127.0.0.1:3000
用户访问:
1https://example.com
Nginx 把请求转发到:
1http://127.0.0.1:3000
常见结构:
1用户浏览器 2 ↓ 3域名 / HTTPS 4 ↓ 5Nginx 6 ├── app1.example.com → 127.0.0.1:3000 7 ├── app2.example.com → 127.0.0.1:4000 8 └── api.example.com → 127.0.0.1:5000
这样做的好处:
- 多个应用可以共用同一台服务器。
- 公网只开放 80/443,内部应用端口不用暴露。
- HTTPS 证书统一由 Nginx 管理。
- 应用重启或换端口时,只需要调整反代配置。
2. 常见 Nginx 配置位置
主配置通常在:
1/etc/nginx/nginx.conf
常见站点配置目录:
1/etc/nginx/conf.d/ 2/etc/nginx/sites-available/ 3/etc/nginx/sites-enabled/
Ubuntu / Debian 常见结构:
1/etc/nginx/nginx.conf 2/etc/nginx/sites-available/default 3/etc/nginx/sites-enabled/default
CentOS / Rocky / AlmaLinux 常见结构:
1/etc/nginx/nginx.conf 2/etc/nginx/conf.d/*.conf
3. 如何找到已有网站的 Nginx 配置
测试 Nginx 配置并查看主配置路径:
1sudo nginx -t
查看主配置引用了哪些目录:
1sudo grep -R "include" /etc/nginx/nginx.conf
搜索所有反向代理配置:
1sudo grep -R "proxy_pass" /etc/nginx
如果知道应用端口,比如 3000,可以直接搜:
1sudo grep -R "3000" /etc/nginx
看到类似输出:
1/etc/nginx/conf.d/my-app.conf: proxy_pass http://127.0.0.1:3000;
说明对应配置文件是:
1/etc/nginx/conf.d/my-app.conf
4. 基础反向代理配置
假设应用运行在:
1127.0.0.1:3000
域名是:
1example.com
Nginx 配置:
1server { 2 listen 80; 3 server_name example.com www.example.com; 4 5 location / { 6 proxy_pass http://127.0.0.1:3000; 7 proxy_http_version 1.1; 8 9 proxy_set_header Host $host; 10 proxy_set_header X-Real-IP $remote_addr; 11 proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 12 proxy_set_header X-Forwarded-Proto $scheme; 13 } 14}
含义:
listen 80:监听 HTTP 端口。server_name:匹配访问的域名。proxy_pass:转发到内部应用地址。proxy_set_header:把真实访问来源、协议、域名等信息传给后端。
5. 新增一个子域名反代
假设新增应用:
1子域名:app2.example.com 2内部端口:4000
新增配置文件:
1sudo nano /etc/nginx/conf.d/app2.conf
写入:
1server { 2 listen 80; 3 server_name app2.example.com; 4 5 location / { 6 proxy_pass http://127.0.0.1:4000; 7 proxy_http_version 1.1; 8 9 proxy_set_header Host $host; 10 proxy_set_header X-Real-IP $remote_addr; 11 proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 12 proxy_set_header X-Forwarded-Proto $scheme; 13 } 14}
检查配置:
1sudo nginx -t
重载:
1sudo systemctl reload nginx
6. 子域名需要做 DNS 解析
Nginx 配置只负责服务器内部转发,域名能不能到服务器,要看 DNS。
例如要使用:
1app2.example.com
在域名 DNS 控制台添加:
1记录类型:A 2主机记录:app2 3记录值:服务器公网 IP 4TTL:默认
如果希望所有子域名都指向服务器,也可以添加泛解析:
1记录类型:A 2主机记录:* 3记录值:服务器公网 IP
但更推荐明确添加需要的子域名,比较清晰。
7. 配置 HTTPS
常用工具是 Certbot。
Ubuntu / Debian:
1sudo apt update 2sudo apt install certbot python3-certbot-nginx
CentOS / Rocky / AlmaLinux:
1sudo yum install certbot python3-certbot-nginx
给域名申请 HTTPS:
1sudo certbot --nginx -d example.com -d www.example.com
给子域名申请 HTTPS:
1sudo certbot --nginx -d app2.example.com
测试自动续期:
1sudo certbot renew --dry-run
申请 HTTPS 前,先确认:
- DNS 已经解析到服务器。
- 80 端口可以访问。
- Nginx 配置测试通过。
8. 防火墙应该开放哪些端口
使用 Nginx 反代时,公网通常只需要开放:
122 SSH 280 HTTP 3443 HTTPS
内部应用端口不建议直接开放,例如:
13000 24000 35000
这些端口应只给服务器本机访问。
Ubuntu / Debian:ufw
查看状态:
1sudo ufw status verbose
开放 HTTP / HTTPS:
1sudo ufw allow 80/tcp 2sudo ufw allow 443/tcp 3sudo ufw reload
CentOS / Rocky / AlmaLinux:firewalld
查看状态:
1sudo firewall-cmd --state 2sudo firewall-cmd --list-all
开放 HTTP / HTTPS:
1sudo firewall-cmd --permanent --add-service=http 2sudo firewall-cmd --permanent --add-service=https 3sudo firewall-cmd --reload
云服务商安全组
云服务器通常还有安全组/防火墙入站规则。
至少开放:
1TCP 22 2TCP 80 3TCP 443
如果安全组没开放 80/443,服务器内部配置正确也无法公网访问。
9. 查看端口监听状态
查看当前监听端口:
1sudo ss -lntp
理想状态:
10.0.0.0:80 nginx 20.0.0.0:443 nginx 3127.0.0.1:3000 node 4127.0.0.1:4000 node
含义:
0.0.0.0:80:公网可访问 HTTP。0.0.0.0:443:公网可访问 HTTPS。127.0.0.1:3000:只有服务器本机可访问。127.0.0.1:4000:只有服务器本机可访问。
如果应用显示为:
10.0.0.0:3000
说明它监听所有网卡。不是绝对不能用,但建议通过防火墙限制,不要对公网开放应用端口。
10. 路径反代:用同一个域名挂多个应用
除了子域名,也可以用路径区分:
1example.com/app1/ 2example.com/app2/
示例:
1server { 2 listen 80; 3 server_name example.com; 4 5 location /app1/ { 6 proxy_pass http://127.0.0.1:3000/; 7 proxy_http_version 1.1; 8 9 proxy_set_header Host $host; 10 proxy_set_header X-Real-IP $remote_addr; 11 proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 12 proxy_set_header X-Forwarded-Proto $scheme; 13 } 14 15 location /app2/ { 16 proxy_pass http://127.0.0.1:4000/; 17 proxy_http_version 1.1; 18 19 proxy_set_header Host $host; 20 proxy_set_header X-Real-IP $remote_addr; 21 proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 22 proxy_set_header X-Forwarded-Proto $scheme; 23 } 24}
注意:路径部署经常需要应用本身支持 base path,否则静态资源、接口路径可能出错。多数情况下,子域名部署更省心。
11. 常用 Nginx 命令
检查配置:
1sudo nginx -t
重载配置:
1sudo systemctl reload nginx
重启 Nginx:
1sudo systemctl restart nginx
查看状态:
1sudo systemctl status nginx
查看错误日志:
1sudo tail -n 100 /var/log/nginx/error.log
查看访问日志:
1sudo tail -n 100 /var/log/nginx/access.log
持续查看错误日志:
1sudo tail -f /var/log/nginx/error.log
12. 常见问题排查
访问域名打不开
检查 DNS:
1ping example.com 2nslookup example.com
检查 Nginx:
1sudo nginx -t 2sudo systemctl status nginx
检查云服务商安全组是否开放 80/443。
出现 502 Bad Gateway
502 通常表示 Nginx 能收到请求,但后端应用不可用。
检查应用端口:
1sudo ss -lntp
检查进程管理工具,例如 PM2:
1pm2 list 2pm2 logs 应用名
确认 Nginx 端口和应用端口一致:
1proxy_pass http://127.0.0.1:3000;
修改配置后没生效
每次改完 Nginx 都要执行:
1sudo nginx -t 2sudo systemctl reload nginx
HTTPS 证书申请失败
检查:
- DNS 是否已经解析到服务器。
- 80 端口是否开放。
- HTTP 是否能正常访问。
- Nginx 配置是否通过
sudo nginx -t。
一个域名进了错误的网站
可能是多个 server 块的 server_name 配置冲突,或者命中了默认站点。
排查:
1sudo grep -R "server_name" /etc/nginx
确认每个域名只对应正确的站点配置。
13. 推荐使用习惯
- 一个应用对应一个 Nginx 配置文件,例如
my-app.conf。 - 后端服务尽量只监听本机地址或通过防火墙限制。
- 公网只开放 80/443。
- 每次改 Nginx 前先备份配置。
- 每次改完都执行
sudo nginx -t。 - 应用进程用 PM2、systemd、Docker 等工具守护。
- 子域名部署通常比路径部署更省心。
14. 通用模板
把下面的域名和端口替换成自己的即可:
1server { 2 listen 80; 3 server_name app.example.com; 4 5 location / { 6 proxy_pass http://127.0.0.1:3000; 7 proxy_http_version 1.1; 8 9 proxy_set_header Host $host; 10 proxy_set_header X-Real-IP $remote_addr; 11 proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 12 proxy_set_header X-Forwarded-Proto $scheme; 13 } 14}
检查并重载:
1sudo nginx -t 2sudo systemctl reload nginx