在前端项目部署中,多个应用共用一台服务器是极其常见的场景,核心思路只有两个词:反向X_X 和 端口隔离。
作为技术人员,我们通常不会让多个前端应用直接监听不同的端口暴露给公网(比如 http://IP:8081, http://IP:8082),因为这样既不美观也不利于管理。最主流、最稳健的方案是使用 Nginx 作为反向X_X服务器,通过域名或路径将请求分发到不同的后端服务或本地静态资源目录。
以下是几种主流的实施方案,按推荐程度排序:
方案一:基于域名的虚拟主机(Virtual Host)—— 最推荐
这是生产环境中最标准的做法。假设你有一台云服务器(如阿里云 ECS、腾讯云 CVM),拥有一个主域名 example.com。
-
前提条件:
- 服务器已安装 Nginx。
- 你有多个子域名,例如
app1.example.com和app2.example.com,并已解析到该服务器 IP。 - 你的前端项目已经构建好(
npm run build),生成了dist或build文件夹。
-
Nginx 配置示例 (
/etc/nginx/conf.d/default.conf):
# 应用 1:app1.example.com
server {
listen 80;
server_name app1.example.com;
root /var/www/app1/dist; # 指向应用1的构建产物目录
index index.html;
location / {
try_files $uri $uri/ /index.html; # Vue/React 等单页应用必须配置,防止刷新404
}
# 可选:配置 HTTPS(使用 Let's Encrypt 免费证书)
# listen 443 ssl;
# ssl_certificate /path/to/cert.pem;
# ssl_certificate_key /path/to/cert.key;
}
# 应用 2:app2.example.com
server {
listen 80;
server_name app2.example.com;
root /var/www/app2/dist; # 指向应用2的构建产物目录
index index.html;
location / {
try_files $uri $uri/ /index.html;
}
}
- 优点:
- 结构清晰,每个应用独立管理。
- 易于扩展,新增应用只需加一个
server块。 - 支持 HTTPS,安全性高。
- 对 SEO 友好(如果使用 SSR)。
方案二:基于路径的反向X_X(Path-based Routing)
如果你只有一个域名(如 example.com),但想部署多个应用,可以通过 URL 路径来区分。
example.com/admin-> 管理后台应用example.com/user-> 用户前台应用
- Nginx 配置示例:
server {
listen 80;
server_name example.com;
# 管理后台应用
location /admin {
alias /var/www/admin-app/dist; # 注意用 alias 而不是 root
index index.html;
try_files $uri $uri/ /admin/index.html; # 注意最后的路径要匹配
}
# 用户前台应用
location /user {
alias /var/www/user-app/dist;
index index.html;
try_files $uri $uri/ /user/index.html;
}
}
- 注意事项:
- 前端路由配置:你需要确保每个前端应用在构建时,
publicPath或base配置正确。例如,在 Vite 中设置base: '/admin/',在 Webpack 中设置output.publicPath: '/admin/'。否则,静态资源(JS/CSS)加载会失败。 - 复杂度较高:需要仔细处理路径映射,容易出错。
- 前端路由配置:你需要确保每个前端应用在构建时,
方案三:Docker + Nginx —— 现代化运维首选
如果你希望实现“一次构建,到处运行”,并且便于版本管理和隔离,推荐使用 Docker。
- 为每个应用编写 Dockerfile:
# Dockerfile for App1
FROM nginx:alpine
COPY ./dist /usr/share/nginx/html
COPY ./nginx.conf /etc/nginx/conf.d/default.conf
EXPOSE 80
CMD ["nginx", "-g", "daemon off;"]
- 编排服务 (
docker-compose.yml):
version: '3'
services:
app1:
build: ./app1
ports:
- "8081:80"
volumes:
- ./app1/nginx.conf:/etc/nginx/conf.d/default.conf
app2:
build: ./app2
ports:
- "8082:80"
volumes:
- ./app2/nginx.conf:/etc/nginx/conf.d/default.conf
nginx-proxy:
image: nginx:alpine
ports:
- "80:80"
volumes:
- ./proxy-nginx.conf:/etc/nginx/conf.d/default.conf
depends_on:
- app1
- app2
- 反向X_X Nginx 配置 (
proxy-nginx.conf):
upstream app1_backend {
server app1:80;
}
upstream app2_backend {
server app2:80;
}
server {
listen 80;
location / {
proxy_pass http://app1_backend;
}
location /api {
proxy_pass http://app2_backend;
}
}
说明:这里为了简化,展示了两个应用分别监听不同内部端口,由外部 Nginx 统一转发。更复杂的场景可以使用 Traefik 或 Consul Template 自动发现服务。
关键注意事项与最佳实践
-
静态资源缓存策略:
前端项目通常包含大量 JS/CSS 文件,且文件名带有 Hash(如app.a1b2c3.js)。务必在 Nginx 中配置长期缓存,以减少服务器压力和提升用户体验:location ~* .(js|css|png|jpg|jpeg|gif|ico|svg)$ { expires 30d; add_header Cache-Control "public, immutable"; } -
SPA 应用的 history 模式:
如果你的前端框架(Vue Router, React Router)使用了history模式,必须配置try_files,将所有非静态资源的请求重定向到index.html,交由前端路由处理。否则,用户直接访问/about会返回 404。 -
安全加固:
- 不要直接暴露服务器 IP 和端口。
- 使用防火墙(如阿里云安全组、腾讯云云防火墙)只开放 80/443 端口。
- 配置 HTTPS 证书,避免浏览器提示“不安全”。
- 定期更新 Nginx 版本,修复已知漏洞。
-
监控与维护:
- 使用 PM2 或 systemd 管理 Nginx 进程,确保崩溃后自动重启。
- 配置日志轮转(logrotate),避免 access.log 和 error.log 无限增长占满磁盘。
-
国内云厂商特定建议:
- 阿里云:建议使用 ALB(应用型负载均衡) 替代自建 Nginx,尤其在高并发场景下,ALB 支持基于域名的路由规则,无需手动维护配置文件,且自带 SSL 卸载能力。
- 腾讯云:类似地,可使用 CLB(经典负载均衡) 或 TKE(容器服务) 进行部署。
- 华为云:推荐 ELB(弹性负载均衡)。
总结
对于大多数中小型项目,Nginx + 多域名虚拟主机 是最简单、高效、易维护的方案。如果追求自动化和微服务架构,则选择 Docker + Nginx Proxy。无论哪种方式,核心都是利用反向X_X技术,将用户的 HTTP 请求根据域名或路径,精准地转发到服务器上对应的应用实例。
CLOUD云枢