Skip to content

Docker 生产环境部署指南

本指南介绍如何使用 Docker 和 Docker Compose 将 VUP 项目部署到生产环境。此部署方案适用于完整的全栈应用(API + 前端 + 数据库),针对 DAU ≤ 5000 的应用进行了优化。

什么是 Docker 部署

Docker 部署提供:

  • 容器化 - 每个服务都有独立的环境
  • 易于更新 - 通过替换文件并重启即可更新,无需重建镜像
  • 资源管理 - CPU 和内存限制,防止资源耗尽
  • 服务编排 - 使用单个命令管理多个服务(数据库、API、前端、nginx)
  • 卷映射 - 直接文件映射,便于更新而无需重建

前置要求

开始之前,请确保您已安装:

  • Docker >= 20.10
  • Docker Compose >= 2.0
  • 服务器 至少 2GB RAM 和 2 CPU 核心
  • 域名(可选,用于 HTTPS)

推荐的部署目录

对于生产环境部署,建议使用标准的 Linux 目录结构:

推荐路径: /opt/vup/opt/vup-cli

这遵循 Linux FHS(文件系统层次结构标准)约定,其中 /opt 用于可选的应用软件包。

设置部署目录

bash
# 创建部署目录
sudo mkdir -p /opt/vup
sudo chown $USER:$USER /opt/vup

# 将 deploy 目录复制到推荐位置
cp -r /path/to/project-vue/deploy/* /opt/vup/

# 或者克隆/复制整个 deploy 目录
cd /opt/vup

目录结构

设置完成后,您的部署目录应如下所示:

/opt/vup/
├── docker-compose.yml
├── .env
├── builds/
├── nginx/
├── scripts/
├── data/
├── logs/
└── backups/

注意: 本指南中的所有路径都假设部署在 /opt/vup。如果您使用不同的目录,请相应调整路径。

快速开始

1. 设置部署目录

bash
# 创建并进入部署目录
sudo mkdir -p /opt/vup
sudo chown $USER:$USER /opt/vup
cd /opt/vup

# 从项目复制 deploy 目录
cp -r /path/to/project-vue/deploy/* /opt/vup/

2. 准备环境变量

在部署目录创建 .env 文件:

bash
cd /opt/vup
cp .env.example .env

编辑 .env 文件,配置您的设置:

bash
# 数据库配置
MYSQL_DATABASE=vup_db
MYSQL_USER=vup_user
MYSQL_PASSWORD=your_secure_password
MYSQL_ROOT_PASSWORD=your_root_password
MYSQL_PORT=3306

# API 配置
CORS_ORIGIN=https://yourdomain.com
JWT_SECRET=your_jwt_secret_key
JWT_EXPIRES_IN=7d
JWT_REFRESH_EXPIRES_IN=30d
UPLOAD_MAX_FILE_SIZE=1073741824
UPLOAD_BASE_URL=https://yourdomain.com/uploads

# 前端配置
API_BASE_URL=https://yourdomain.com/api
APP_BASE_URL=https://yourdomain.com

# 端口配置
HTTP_PORT=80
HTTPS_PORT=443

3. 构建应用

构建您的 API 和 Admin 应用:

bash
# 构建 API
cd apps/nest-template
pnpm build

# 构建 Admin (Nuxt)
cd apps/nuxt-template
pnpm build

4. 复制构建产物

将构建产物复制到部署目录:

bash
# 复制 API 构建产物
cp -r /path/to/project-vue/apps/nest-template/.output /opt/vup/builds/api

# 复制 Admin 构建产物
cp -r /path/to/project-vue/apps/nuxt-template/.output /opt/vup/builds/admin

5. 启动服务

bash
cd /opt/vup

# 启动所有服务
docker compose up -d

# 查看日志
docker compose logs -f

# 检查服务状态
docker compose ps

6. 运行数据库迁移

bash
# 运行迁移
docker compose run --rm migration

服务概览

MariaDB 数据库

  • 容器: vup-mariadb
  • 镜像: mariadb:11.3
  • 端口: 3306(可通过 MYSQL_PORT 配置)
  • 数据卷: ./data/mariadb
  • 备份卷: ./backups/mariadb
  • 资源限制: 0.8 CPU, 1GB RAM

API 服务

  • 容器: vup-api
  • 镜像: node:20-alpine
  • 端口: 9310(内部)
  • 构建目录: ./builds/api
  • 资源限制: 0.6 CPU, 512MB RAM

Admin 前端服务

  • 容器: vup-admin
  • 镜像: node:20-alpine
  • 端口: 3000(内部,Nuxt SSR)
  • 构建目录: ./builds/admin
  • 资源限制: 0.2 CPU, 256MB RAM

Nginx 反向代理

  • 容器: vup-nginx
  • 镜像: nginx:alpine
  • 端口: 80 (HTTP), 443 (HTTPS)
  • 资源限制: 0.2 CPU, 128MB RAM

迁移服务

  • 容器: migration(一次性使用)
  • 镜像: node:20-alpine
  • Profile: migration(不会自动启动)

配置说明

Docker Compose 配置

docker-compose.yml 文件使用卷映射以便于更新:

  • 优势: 通过替换文件并重启即可更新,无需重建镜像
  • 适用场景: DAU ≤ 5000
  • 更新流程: 替换构建文件 → 重启服务

Nginx 配置

Nginx 作为反向代理,具有以下路由:

  • /api/http://api:9310/api/ - API 服务
  • /admin/http://admin:3000/ - Admin 前端服务
  • /uploads/ → 静态文件服务(从卷挂载)
  • / → 重定向到 /admin/
  • /health → 健康检查端点

功能特性

  1. 反向代理 - API 和 Admin 服务通过反向代理访问
  2. 静态文件服务 - 上传文件通过 Nginx 直接提供
  3. 文件上传支持 - 最大上传大小 1GB
  4. Gzip 压缩 - 启用 Gzip 压缩提升性能
  5. 缓存控制 - 上传文件缓存 30 天
  6. CORS 支持 - 上传文件支持跨域访问

测试 Nginx 配置

bash
# 测试配置文件语法
docker compose exec nginx nginx -t

# 重新加载配置(不中断服务)
docker compose exec nginx nginx -s reload

# 查看日志
docker compose exec nginx tail -f /var/log/nginx/access.log
docker compose exec nginx tail -f /var/log/nginx/error.log

HTTPS 配置(可选)

如果需要启用 HTTPS:

  1. 将 SSL 证书文件放到 nginx/ssl/ 目录:

    • cert.pem - SSL 证书
    • key.pem - SSL 私钥
  2. 取消注释 nginx/conf.d/default.conf 中的 HTTPS server 块

  3. 修改 server_name 为实际域名

  4. 重启 nginx:

bash
docker compose restart nginx

注意: 生产环境建议使用 Let's Encrypt 免费证书。

部署脚本

deploy/scripts/ 目录包含维护工具脚本:

backup.sh - 数据库备份

备份 MariaDB 数据库和上传文件,自动清理旧备份(保留 7 天)。

bash
./scripts/backup.sh

定时任务配置(每日凌晨 2:00):

bash
# 假设部署在 /opt/vup
0 2 * * * /opt/vup/scripts/backup.sh >> /opt/vup/logs/backup.log 2>&1

cleanup.sh - 清理脚本

清理旧日志(保留 30 天)、旧备份(保留 7 天)和 Docker 未使用的资源。检查磁盘使用率。

bash
./scripts/cleanup.sh

定时任务配置(每日凌晨 3:00):

bash
# 假设部署在 /opt/vup
0 3 * * * /opt/vup/scripts/cleanup.sh >> /opt/vup/logs/cleanup.log 2>&1

monitor.sh - 监控脚本

显示服务状态、资源使用情况、磁盘和内存使用、健康检查和告警。

bash
./scripts/monitor.sh

定时任务配置(每小时):

bash
# 假设部署在 /opt/vup
0 * * * * /opt/vup/scripts/monitor.sh >> /opt/vup/logs/monitor.log 2>&1

restore.sh - 数据库恢复

从备份文件恢复数据库。恢复前自动创建临时备份。

bash
# 查看备份列表
ls -lh backups/mariadb/

# 恢复指定备份
./scripts/restore.sh backups/mariadb/backup_20240101_020000.sql.gz

警告: 恢复操作会覆盖当前数据库。恢复前会自动创建临时备份。

设置定时任务

创建设置脚本(/opt/vup/scripts/setup-cron.sh):

bash
#!/bin/bash

# 假设部署在 /opt/vup
DEPLOY_DIR="/opt/vup"

# 备份任务(每日凌晨 2:00)
echo "0 2 * * * ${DEPLOY_DIR}/scripts/backup.sh >> ${DEPLOY_DIR}/logs/backup.log 2>&1" | crontab -

# 清理任务(每日凌晨 3:00)
echo "0 3 * * * ${DEPLOY_DIR}/scripts/cleanup.sh >> ${DEPLOY_DIR}/logs/cleanup.log 2>&1" | crontab -

# 监控任务(每小时)
echo "0 * * * * ${DEPLOY_DIR}/scripts/monitor.sh >> ${DEPLOY_DIR}/logs/monitor.log 2>&1" | crontab -

echo "定时任务已配置"

使其可执行:

bash
chmod +x /opt/vup/scripts/setup-cron.sh
/opt/vup/scripts/setup-cron.sh

确保脚本有执行权限:

bash
chmod +x scripts/*.sh

日常运维

查看日志

bash
# 查看所有服务日志
docker compose logs -f

# 查看特定服务日志
docker compose logs -f api
docker compose logs -f admin
docker compose logs -f nginx
docker compose logs -f mariadb

# 查看本地日志文件
tail -f logs/api/app.log
tail -f logs/admin/app.log
tail -f nginx/logs/access.log
tail -f nginx/logs/error.log

重启服务

bash
# 重启所有服务
docker compose restart

# 重启特定服务
docker compose restart api
docker compose restart admin
docker compose restart nginx

# 停止所有服务
docker compose stop

# 启动所有服务
docker compose start

健康检查

bash
# 检查服务状态
docker compose ps

# 检查 API 健康
curl http://localhost/api/health

# 检查 Admin 健康
curl http://localhost/admin/

# 检查数据库连接
docker compose exec mariadb mysqladmin ping -h localhost

更新应用

  1. 构建新版本:
bash
# 构建 API
cd apps/nest-template
pnpm build

# 构建 Admin
cd apps/nuxt-template
pnpm build
  1. 复制构建产物:
bash
# 备份当前版本(可选)
cp -r /opt/vup/builds/api /opt/vup/builds/api.backup
cp -r /opt/vup/builds/admin /opt/vup/builds/admin.backup

# 复制新构建
cp -r /path/to/project-vue/apps/nest-template/.output /opt/vup/builds/api
cp -r /path/to/project-vue/apps/nuxt-template/.output /opt/vup/builds/admin
  1. 重启服务:
bash
cd /opt/vup
docker compose restart api admin

故障排查

502 Bad Gateway

  • 检查 API 或 Admin 服务是否运行:
    bash
    docker compose ps
  • 检查服务日志:
    bash
    docker compose logs api
    docker compose logs admin
  • 验证 nginx 配置中的服务名称(apiadmin
  • 验证端口(API: 9310, Admin: 3000)

403 Forbidden

  • 检查文件权限:
    bash
    ls -la /opt/vup/data/uploads
  • 验证 uploads 目录是否存在
  • 检查 nginx 配置

413 Request Entity Too Large

  • 检查 nginx 配置中的 client_max_body_size
  • 验证 API 服务的 UPLOAD_MAX_FILE_SIZE 环境变量

数据库连接问题

  • 检查数据库容器状态:
    bash
    docker compose ps mariadb
  • 检查数据库日志:
    bash
    docker compose logs mariadb
  • 验证环境变量:
    bash
    docker compose exec api env | grep MYSQL

服务无法启动

  • 检查资源限制(CPU/内存)
  • 检查磁盘空间:
    bash
    df -h
  • 检查 Docker 日志:
    bash
    docker compose logs

脚本执行问题

  • 检查脚本权限:
    bash
    ls -l scripts/
    chmod +x scripts/*.sh
  • 手动测试脚本:
    bash
    ./scripts/backup.sh

最佳实践

资源管理

  • 定期监控资源使用:
    bash
    docker stats
  • 根据实际使用情况调整 docker-compose.yml 中的资源限制
  • 设置适当的 CPU 和内存限制,防止资源耗尽

备份策略

  • 每日备份: 配置定时任务进行每日数据库备份
  • 备份保留: 至少保留 7 天的备份
  • 测试恢复: 定期测试备份恢复
  • 异地备份: 在单独位置存储备份

监控

  • 使用 monitor.sh 设置每小时监控
  • 监控磁盘使用,防止磁盘满
  • 设置服务故障告警
  • 监控资源使用趋势

安全

  • 为数据库使用强密码
  • 保持 Docker 和镜像更新
  • 生产环境使用 HTTPS
  • 限制数据库端口访问(使用防火墙)
  • 定期审查和更新环境变量

性能优化

  • 在 Nginx 中启用 Gzip 压缩
  • 配置适当的缓存头
  • 监控和优化数据库查询
  • 对静态资源使用 CDN(如适用)

目录结构

推荐的部署目录结构(/opt/vup):

/opt/vup/
├── docker-compose.yml      # Docker Compose 配置
├── .env                    # 环境变量(不在 git 中)
├── builds/                 # 构建产物
│   ├── api/               # API 构建产物
│   └── admin/             # Admin 构建产物
├── nginx/                  # Nginx 配置
│   ├── nginx.conf         # Nginx 主配置
│   ├── conf.d/            # 站点配置
│   │   └── default.conf   # 默认站点配置
│   ├── ssl/               # SSL 证书(可选)
│   └── logs/              # Nginx 日志
├── scripts/                # 部署脚本
│   ├── backup.sh          # 数据库备份
│   ├── cleanup.sh         # 清理脚本
│   ├── monitor.sh         # 监控脚本
│   ├── restore.sh         # 数据库恢复
│   └── setup-cron.sh      # 定时任务设置脚本
├── data/                   # 数据卷
│   ├── mariadb/           # 数据库数据
│   └── uploads/            # 上传文件
├── logs/                   # 应用日志
│   ├── api/               # API 日志
│   ├── admin/             # Admin 日志
│   ├── backup.log         # 备份脚本日志
│   ├── cleanup.log        # 清理脚本日志
│   └── monitor.log        # 监控脚本日志
└── backups/               # 备份文件
    ├── mariadb/           # 数据库备份
    └── api/               # API 备份

注意: 如果您部署到不同的目录,请相应调整脚本和定时任务中的所有路径。

相关资源