Nginx 反向代理保姆级教程:从入门到生产高可用(小白友好·零翻车版)

适合谁:在服务器上跑了 Docker 容器、Web 网站或 API 接口,只会敲端口号(如 :8080:8090),面对域名绑定、HTTPS 证书、WebSocket 和 Nginx 配置文件就发懵的初学者。

支持系统:Debian 11/12/13、Ubuntu 20.04/22.04/24.04 LTS(主流云服务器通用,无论是否安装 1Panel / 宝塔均可参考)。

耗时预期:约 20 ~ 30 分钟(跟着一步步敲,学会后一辈子受用)。

做完你将得到:彻底告别丑陋的非标端口(:8080),用优雅的专属域名访问你的所有服务;自带真实访客 IP 透传、大文件上传放行、WebSocket 长连接保活与终身免费 HTTPS 绿锁!

⚠️ 全程唯一保命铁律永远不要在没运行 nginx -t 体检之前直接重启 Nginx! 这个命令是你的“安全气囊”,只要终端提示 test is successful,就永远不可能把服务配崩。


🧭 核心概念:搞懂什么是“反向代理”(10 秒彻底顿悟)

很多新手被“正向代理”和“反向代理”绕晕,其实用一个生活中的比喻立刻就能明白:

【外界访客 / 浏览器】
        │
        ▼ 访问 https://blog.0000996.xyz
┌───────────────────────────────────────────────────────┐
│              🏢 你的云服务器 (VPS)                      │
│                                                       │
│   💁 Nginx(大楼前台总机)                              │
│         │                                             │
│         ├─ 听到找 "blog"  ──► 转接给工位 A (:8090 Halo) │
│         ├─ 听到找 "pan"   ──► 转接给工位 B (:5244 AList)│
│         └─ 听到找 "api"   ──► 转接给工位 C (:5321 接口) │
└───────────────────────────────────────────────────────┘
  • 大白话:Nginx 就是你服务器里唯一的「大楼前台总机」
  • 外面的访客只跟前台打交道(只记域名,永远走标准的 80/443 端口);
  • 前台根据访客报出的域名,在服务器内网默默把请求转交给对应的小黑屋工位(Halo 博客、AList 网盘、内部 API);
  • 外界根本不知道你的服务跑在哪个具体端口上,既优雅、又极其安全!

📋 开始前的准备清单(缺一项都别往下走)

  • [ ] 一台云服务器(VPS):拥有 root 登录权限;
  • [ ] 一个解析好的域名:例如将 blog.example.comapi.example.com 的 A 记录指向你的服务器 IP;
  • [ ] 一个已经跑在本地端口的服务
  • 比如 Docker 跑的 Halo 博客(127.0.0.1:8090)或 AList 网盘(127.0.0.1:5244);
  • [ ] 云厂商控制台放行 80 和 443:在腾讯云/阿里云/AWS 网页安全组中,确保允许外网访问 80/tcp443/tcp

第 1 步:极速安装 Nginx 并验证服务健康

💻 【你本地的电脑】 打开终端连接你的服务器,进入 🖥️ 【服务器窗口】

粘贴执行以下官方标准安装与开机自启命令:

# 1. 刷新仓库并安装 Nginx
export DEBIAN_FRONTEND=noninteractive
apt update && apt install -y nginx

# 2. 启动服务并加入开机自启
systemctl enable --now nginx

# 3. 检查 Nginx 运行状态与版本
nginx -v
systemctl is-active nginx
  • 成功标志:终端输出显示 nginx version: nginx/1.x.x,且最后一行明确返回 active

💡 防冲突小提醒:如果你服务器上装了 1Panel 或宝塔面板,且之前已经在面板里安装了 OpenResty,请先运行 ss -tulpn | grep :80 看一眼 80 端口是否已被占用。未占用的裸机直接跑上述命令即可。


第 2 步:搞懂 Nginx 的“工作台法则”(永远不乱改主配置)

很多新手改崩 Nginx,就是因为一上来就去动 /etc/nginx/nginx.conf,结果改得面目全非无法还原。

工业界标准的最佳实践是模块化管理

目录路径 它的职责与角色 正确使用法则
/etc/nginx/sites-available/ 【配置草稿箱】:存放所有站点的独立配置文件 新建、修改站点配置一律在这里操作
/etc/nginx/sites-enabled/ 【正式生效箱】:只放生效站点的快捷方式(软链接) 绝不在里面新建文件,只用 ln -sf 从草稿箱链接过来
/etc/nginx/nginx.conf 【底层总发动机】:系统级总配置 新手碰都不要碰,保持官方默认

第 3 步:一键生成全功能生产级反代配置

这个配置是经过无数线上高并发业务验证过的黄金模板,原生内置了: 1. 真实访客 IP 透传:后端程序能拿到访客真实 IP,而不是全显示 127.0.0.1; 2. 大文件上传放行:默认放行 100MB 大文件,彻底告别传图报 413 Request Entity Too Large; 3. WebSocket 实时通信:后台实时日志、通知提醒秒级推送不卡死; 4. 长连接超时调优:防止发布大长文或备份时被 Nginx 提前掐断连接(报 504)。

🖥️ 【服务器窗口】 先定义你的两个核心变量(替换为你自己的域名和后端内部端口):

MY_DOMAIN="api.example.com"
UPSTREAM_PORT="8090"

接着,直接整段复制执行以下自包含写入脚本(绝不需要手动碰 vim):

# 1. 写入独立的站点反代配置文件
cat << EOF > /etc/nginx/sites-available/${MY_DOMAIN}.conf
server {
    listen 80;
    listen [::]:80;
    server_name ${MY_DOMAIN};

    # 放行大文件上传(根据需要调大,如 100M)
    client_max_body_size 100M;

    location / {
        # 内部转接核心指令
        proxy_pass http://127.0.0.1:${UPSTREAM_PORT};

        # 核心请求头透传(让后端感知真实的访客与协议)
        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;

        # WebSocket 长连接双向保活支持
        proxy_http_version 1.1;
        proxy_set_header Upgrade \$http_upgrade;
        proxy_set_header Connection "upgrade";

        # 调优连接与读取超时时间(秒)
        proxy_connect_timeout 60s;
        proxy_read_timeout 120s;
        proxy_send_timeout 120s;
    }
}
EOF

# 2. 检查文件是否落地成功
ls -lh /etc/nginx/sites-available/${MY_DOMAIN}.conf
  • 成功标志:终端显示 /etc/nginx/sites-available/你的域名.conf 已成功创建。

第 4 步:激活站点与“保命安全气囊体检”

配置文件写好了,现在我们把它推入生效箱,并执行至关重要的语法安全体检

🖥️ 【服务器窗口】 粘贴执行以下激活与检查命令:

# 1. 创建快捷方式(软链接)到生效目录
ln -sf /etc/nginx/sites-available/${MY_DOMAIN}.conf /etc/nginx/sites-enabled/

# 2. 顺手清理掉默认的“Welcome to nginx”占位网页(避免冲突)
rm -f /etc/nginx/sites-enabled/default

# 3. 核心安全气囊:Nginx 语法预检
nginx -t
  • 成功标志:终端屏幕必须打出这两行绿色通过指标: text nginx: the configuration file /etc/nginx/nginx.conf syntax is ok nginx: configuration file /etc/nginx/nginx.conf test is successful

只要看到 test is successful,立刻放心地让 Nginx 平滑重载:

systemctl reload nginx
  • 🗣️ 大白话:reload 是优雅热重载,旧的连接不会断开,新的配置瞬间生效,完全不需要先 stop 再 start!

第 5 步:开启终身免费 HTTPS 绿锁(两种最爽方案)

现在你的域名通过 HTTP 已经可以正常访问了,但现代网站必须带小绿锁(HTTPS)。根据你的架构选择以下任意一种:

🌟 方案 A:Cloudflare 边缘极速小黄云(小白首选,零运维)

如果你的域名托管在 Cloudflare,这是全世界最优雅省心的方式: 1. 💻 【浏览器】 打开 Cloudflare 仪表盘,找到你的域名 DNS 解析; 2. 确保你的域名 A 记录打开了橙色小云朵(已代理); 3. 点击左侧菜单 「SSL/TLS」,加密模式选择 「Flexible(灵活)」「Full(完全)」; 4. 🏁 搞定! 你的 Nginx 服务器内部完全不需要装任何证书,Cloudflare 全球边缘 CDN 会自动为访客提供全球顶级免费 HTTPS 绿锁!


🛡️ 方案 B:Certbot 官方全自动证书(不走 CDN 或纯直连推荐)

如果你没用 Cloudflare,或者想在服务器本地生成纯正的 Let's Encrypt 证书:

🖥️ 【服务器窗口】 一行命令安装 Certbot 并让它自动配置 Nginx:

# 1. 安装 Certbot 自动化工具
apt install -y certbot python3-certbot-nginx

# 2. 一键自动申请证书并自动改写 Nginx 为 HTTPS(将命令里的域名换成你的)
certbot --nginx -d ${MY_DOMAIN} --non-interactive --agree-tos --register-unsafely-without-email --redirect
  • 成功标志:Certbot 输出 Congratulations! Successfully deployed certificate for ...,它会自动把 HTTP 访问 301 重定向到 HTTPS!
  • 💡 自动续期保障:Certbot 会自动注册 systemd 定时器,到期前 30 天静默自动续签,终身免维护。

第 6 步:多域名共存实战(一台服务器跑 N 个网站)

很多小白最困惑的一点:“我手里只有一台便宜 VPS,但我想同时挂一个博客、一个网盘、还有一个图床,端口全是 80/443,会不会打架?

答案是:完全不会!Nginx 最擅长的就是这个。

你只需要按下面的结构,为每一个服务建一个独立的 .conf 文件:

/etc/nginx/sites-available/
├── blog.0000996.xyz.conf   ──► 转给 127.0.0.1:8090 (Halo博客)
├── pan.0000996.xyz.conf    ──► 转给 127.0.0.1:5244 (AList网盘)
└── img.0000996.xyz.conf    ──► 转给 127.0.0.1:8080 (图床服务)

每次想加新网站: 1. 回到【第 3 步】,把 MY_DOMAINUPSTREAM_PORT 换成新的; 2. 执行写入脚本; 3. 回到【第 4 步】,ln -sf 链接并执行 nginx -t; 4. systemctl reload nginx
几秒钟之内,新域名瞬间上线,老网站业务丝毫不受影响!🚀


🚑 翻车急救站(新手最怕的 5 大异常与解药)

异常现象 真实根因 对应一秒救命招式
浏览器提示 502 Bad Gateway Nginx 活得好好的,但后端小黑屋里的服务挂了或端口填错 1. 检查内部端口:在服务器运行 curl -I http://127.0.0.1:你的端口
2. 检查 Docker 容器:docker ps 看看对应容器是不是退出了(Exited)。
浏览器提示 连接超时 (Timed Out) 云厂商控制台外部门禁没放行 检查【准备清单】,去云服务器控制台安全组核对 80 和 443 端口是否处于「允许」状态。
执行 nginx -t 报错 syntax error 配置文件里少写了分号 ; 或大括号不闭合 报错信息会明确指明出问题的行号(例如 line 15),使用 cat -n /etc/nginx/sites-available/xxx.conf 对照行号补上分号即可。
上传稍大的图片或文件提示 413 Too Large Nginx 默认限制上传不能超过 1MB 检查配置里是否有 client_max_body_size 100M;,改好后记得 systemctl reload nginx
提示 Address already in use 80 端口被占 Apache 或旧的进程抢占了端口 运行 lsof -i :80ss -tulpn | grep :80,找到占用进程的 PID 并 kill 掉,再重启 Nginx。

🎓 毕业全维度自检清单

核对以下 5 项指标,全部通过即代表你的反向代理网关已达到生产级稳定标准:

  • [ ] 语法体检全绿:服务器执行 nginx -t 明确返回 syntax is oktest is successful
  • [ ] 域名直连成功:在浏览器输入 https://你的域名 能准确打开目标服务,不需要在后面尾随端口号;
  • [ ] 访客真实 IP 透传:查看后端服务或容器日志,访问来源清晰记录着你的真实手机/宽带 IP,而不是内网环回地址;
  • [ ] 后台长连接正常:访问后台页面或实时刷新组件,F12 控制台不报 WebSocket 101 连接失败;
  • [ ] 开机自动守护:Nginx 服务处于 enabled 状态,服务器重启后自动恢复全部站点的路由反代!