Ubuntu Nginx站点部署实录:从配置详解到自动化脚本
Ubuntu Nginx站点部署实录:从配置详解到自动化脚本
前言:
最近为了把跑在内网8090端口的博客服务发布到公网,我折腾了一番 Nginx。
目标很简单:通过域名blog.twopair.cn访问,由 HTTP 自动跳转 HTTPS,且以后要能轻松管理多个站点。
这里的记录涵盖了从环境安装、配置文件原理详解,到最终封装自动化脚本的全过程。
一、 起步:环境与基础
在 Ubuntu 20.04/22.04 上,第一步永远是把环境铺好。
# 1. 更新源并安装 Nginx 和解压工具
sudo apt update
sudo apt install nginx unzip -y
# 2. 确认防火墙放行 HTTP/HTTPS,否则外网白搭
sudo ufw allow 'Nginx Full'
二、 核心逻辑:Nginx 的“仓库”与“柜台”
Ubuntu 下 Nginx 的目录结构设计非常巧妙,理解这个逻辑是手动配置的基础:
/etc/nginx/sites-available/(仓库):
存放配置文件的原稿。写在这里的文件 Nginx 是不读的,相当于“草稿箱”。/etc/nginx/sites-enabled/(柜台):
存放指向仓库文件的软链接(快捷方式)。Nginx 启动时只加载这里的内容。
我的管理逻辑:
- 上线:用
ln -s把仓库里的文件链接到柜台。 - 下线:用
rm删掉柜台里的链接(原稿保留,随时可恢复)。
三、 深度解析:Nginx 配置文件写了什么?
在使用脚本“一键生成”之前,必须搞懂配置文件里每一行的含义。以我的 blog.twopair.cn 为例,一个标准的HTTPS + 反向代理配置如下:
1. 证书存放规范
为了不乱,我统一将证书存放在 /etc/nginx/cert/<域名>/ 目录下:
.pem/.crt:公钥/证书链。.key:私钥(注意权限保护)。
2. 配置文件拆解
通常包含两个 server 块。
第一部分:HTTP 强制跳转 HTTPS
拦截所有 80 端口请求,将其扔给 443 端口。
server {
listen 80;
server_name blog.twopair.cn; # 匹配我的域名
# 301 永久重定向到 HTTPS,保留原本的请求路径
return 301 https://$host$request_uri;
}
第二部分:HTTPS 核心配置
server {
# --- 基础监听 ---
listen 443 ssl;
server_name blog.twopair.cn;
# --- SSL 证书配置 ---
# 这里指向我解压后的证书路径
ssl_certificate /etc/nginx/cert/blog.twopair.cn/fullchain.pem;
ssl_certificate_key /etc/nginx/cert/blog.twopair.cn/privkey.key;
# --- 关键:解决上传报错 ---
# 默认 Nginx 限制上传 1MB,博客传大图会报 413 Too Large
# 手动改成了 100M
client_max_body_size 100M;
# --- 反向代理设置 (连接后端) ---
location / {
proxy_pass http://127.0.0.1:8090; # 转发给本地 8090 端口
# --- 请求头传递 (Header) ---
# 如果不加下面这几行,后端服务拿到的 IP 全是 127.0.0.1
# 这会导致日志分析和 IP 限制功能失效
proxy_set_header Host $host; # 传递原始域名
proxy_set_header X-Real-IP $remote_addr; # 传递用户真实IP
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme; # 告诉后端原本是 https
}
}
四、 终极方案:自动化管理脚本
为了以后不再手动复制粘贴上述配置,我让AI写了一个脚本 vhost_manager.sh。
它会自动部署站点:解压证书 -> 生成上述配置 -> 建立软链接 -> 重载 Nginx。
1. 脚本代码
保存为 vhost_manager.sh 并赋予执行权限 chmod +x vhost_manager.sh。
#!/bin/bash
# Nginx 站点管理工具
case "$1" in
deploy)
# 部署模式:需要 域名、端口、证书zip包
DOMAIN=$2; PORT=$3; ZIP_PATH=$4
CERT_DIR="/etc/nginx/cert/$DOMAIN"
CONF_PATH="/etc/nginx/sites-available/$DOMAIN"
echo ">>> [1/4] 准备证书目录: $CERT_DIR"
sudo mkdir -p "$CERT_DIR"
sudo unzip -j -o "$ZIP_PATH" -d "$CERT_DIR" > /dev/null
# 智能识别证书文件 (无论文件名叫什么)
PEM=$(sudo find "$CERT_DIR" -name "*.pem" -o -name "*.crt" | head -n 1)
KEY=$(sudo find "$CERT_DIR" -name "*.key" | head -n 1)
if [ -z "$PEM" ] || [ -z "$KEY" ]; then
echo "错误:ZIP 包中未找到 .pem/.crt 或 .key 文件!"
exit 1
fi
echo ">>> [2/4] 生成 Nginx 配置..."
sudo bash -c "cat > $CONF_PATH <<EOF
server {
listen 80;
server_name $DOMAIN;
return 301 https://\$host\$request_uri;
}
server {
listen 443 ssl;
server_name $DOMAIN;
ssl_certificate $PEM;
ssl_certificate_key $KEY;
ssl_session_timeout 5m;
ssl_protocols TLSv1.2 TLSv1.3;
ssl_ciphers HIGH:!aNULL:!MD5;
# 允许最大上传 100M
client_max_body_size 100M;
location / {
proxy_pass http://127.0.0.1:$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;
}
}
EOF"
echo ">>> [3/4] 激活站点..."
sudo ln -sf "$CONF_PATH" "/etc/nginx/sites-enabled/"
echo ">>> [4/4] 重载服务..."
sudo nginx -t && sudo systemctl reload nginx
echo ">>> 成功!https://$DOMAIN 现在指向本地端口 $PORT"
;;
enable)
# 上线:恢复软链接
sudo ln -sf "/etc/nginx/sites-available/$2" "/etc/nginx/sites-enabled/"
sudo nginx -t && sudo systemctl reload nginx
echo ">>> 站点 $2 已重新上线"
;;
disable)
# 下线:断开软链接,保留配置
sudo rm -f "/etc/nginx/sites-enabled/$2"
sudo systemctl reload nginx
echo ">>> 站点 $2 已下线 (配置保留)"
;;
remove)
# 销毁:彻底清理所有相关文件
sudo rm -f "/etc/nginx/sites-enabled/$2"
sudo rm -f "/etc/nginx/sites-available/$2"
sudo rm -rf "/etc/nginx/cert/$2"
sudo systemctl reload nginx
echo ">>> 站点 $2 已彻底移除"
;;
status)
echo "--- [已上线站点] ---"
ls /etc/nginx/sites-enabled/
;;
*)
echo "用法: $0 {deploy|enable|disable|remove|status} ..."
;;
esac
五、 实战演示:我的博客部署过程
假设我已经把申请好的 SSL 证书压缩包 blog_cert.zip 上传到了服务器,且博客程序已经在 8090 端口运行。
1. 一键部署
运行脚本,填入我的域名和端口:
./vhost_manager.sh deploy blog.twopair.cn 8090 ./blog_cert.zip
执行后,脚本会自动解压证书、写入上面的那套配置、并重载Nginx部署站点。
2. 日常维护
- 临时维护博客:
./vhost_manager.sh disable blog.twopair.cn
(此时用户访问会挂掉,但配置和证书都在) - 维护完毕上线:
./vhost_manager.sh enable blog.twopair.cn - 以后不再用这个站了:
./vhost_manager.sh remove blog.twopair.cn
(彻底删除干净)
六、 避坑指南
在折腾过程中遇到过几个坑,特此记录:
- 413 Request Entity Too Large:
- 现象:博客上传图片稍微大点就报错。
- 原因:Nginx 默认限制 1MB。
- 解决:脚本里我已经加了
client_max_body_size 100M;。
本文是原创文章,采用 CC BY-NC-ND 4.0 协议,完整转载请注明来自 Twopair
评论
匿名评论
隐私政策
你无需删除空行,直接评论以获取最佳展示效果