Skip to content

部署说明

一台 Ubuntu 服务器 + 域名即可完成全栈部署。

与代码一致的生产默认路径(宝塔)deploy/docker-compose.prod.yml 仅编排 MySQL、Redis、Go backend 三个容器;前端静态文件deploy.sh 调用 build-frontend-inner.sh 构建并写入本机目录 FRONTEND_DIST_PATH(宝塔 www 站点根);SSL / Nginx 由宝塔站点配置(或自建 Nginx),不是 compose 里的 shice-nginx 容器。下文「§3 全容器 Nginx」为可选/历史示意,若未单独启用对应 compose 栈则不存在这些容器名。


1. 服务器要求

项目最低推荐
系统Ubuntu 20.04 / Debian 11Ubuntu 22.04+
CPU2 核4 核
内存4 GB8 GB
磁盘20 GB SSD40 GB+ SSD
软件Docker 24+、Docker Compose v2
网络公网 IP + 域名

2. 目录结构

部署相关文件全部在 deploy/ 目录下:

deploy/
├── docker-compose.yml # 开发:MySQL + Redis + Qdrant + MinIO
├── docker-compose.prod.yml              # 生产:mysql + redis + backend(无 Nginx 容器)
├── docker-compose.frontend-builder.yml  # 可选:compose 内构建前端镜像时
├── deploy.sh                            # 宝塔一键:前端静态 → FRONTEND_DIST_PATH;后端 build 或 pull
├── build-frontend-inner.sh              # pnpm + vite 构建(被 deploy.sh 或 node 容器调用)
├── build-push-backend-image.sh          # 本地/CI:buildx 推送后端镜像
├── .env.example                         # 含 BACKEND_IMAGE、BACKEND_PULL_ONLY 等
├── config.prod.yaml                     # 后端生产配置(挂载进容器)
├── init.sql
└── nginx/                               # 参考配置(宝塔站点可照抄)
    ├── default.conf
    └── baota-*.conf

3. 生产架构(当前默认:宝塔 Nginx + Docker 应用)

text
  Internet (HTTPS)
       |
  [宝塔 Nginx 宿主机 ]
  www  -> FRONTEND_DIST_PATH(静态 SPA)
  api  -> http://127.0.0.1:8080
       |
  [ Docker: shice-backend ]
       +-- shice-mysql
       +-- shice-redis
单元说明
前端静态deploy.sh 写入 FRONTEND_DIST_PATHFRONTEND_BUILD_WITH_DOCKER 控制是否用 Docker 跑 Node
shice-backend默认 docker compose build;可设 BACKEND_PULL_ONLY=1BACKEND_IMAGE 仅 pull
shice-mysql / shice-redisdocker-compose.prod.yml 一致,端口不暴露公网

3.1 可选:全容器 Nginx(未包含在默认 prod compose)

若自行扩展 compose(增加 Nginx 容器与前端静态卷),可能出现文档旧版中的 shice-nginxshice-frontend-builder 等命名。本仓库默认的 deploy.sh + docker-compose.prod.yml 不创建这些服务


4. 一键部署步骤

4.1 安装 Docker

bash
# Ubuntu
curl -fsSL https://get.docker.com | sh
sudo usermod -aG docker $USER
# 重新登录 shell 使 docker 组生效

4.2 克隆代码

bash
git clone <repo-url> && cd shice_dev

4.3 配置环境变量

bash
cd deploy
cp .env.example .env
vim .env

.env 中必须修改的字段:

变量说明示例
MYSQL_ROOT_PASSWORDMySQL root 密码随机强密码
MYSQL_PASSWORD应用数据库密码随机强密码
REDIS_PASSWORDRedis 密码(可选)留空或设置密码
JWT_SECRETJWT 签名密钥,至少 32 位随机字符串openssl rand -hex 32
AI_API_KEYAI 模型 API Key(DeepSeek / OpenAI)sk-xxx
DOMAIN你的域名(用于推导默认 VITE_API_BASE_URLshice.example.com
FRONTEND_DIST_PATH前端静态输出目录(宝塔站点根)/www/wwwroot/www.example.com
VITE_API_BASE_URL前端构建时 API 根路径(须含 /api/v1https://api.example.com/api/v1
FRONTEND_BUILD_WITH_DOCKER1 用官方 Node 镜像构建;0 用宿主机 pnpm01
BACKEND_IMAGE预构建后端镜像全名(与 BACKEND_PULL_ONLY 联用)ghcr.io/org/shice-backend:tag
BACKEND_PULL_ONLY1deploy.sh 对 backend 执行 pull 而非 build01

4.4 同步生产配置

编辑 config.prod.yaml,确保以下值与 .env 一致:

yaml
database:
  dsn: "shice:<MYSQL_PASSWORD>@tcp(mysql:3306)/shice?charset=utf8mb4&parseTime=True&loc=Local"

redis:
  addr: "redis:6379"
  password: "<REDIS_PASSWORD>"

jwt:
  secret: "<JWT_SECRET>"

ai.api_key 留空即可,运行时从环境变量 AI_API_KEY 注入。

4.5 执行部署

bash
chmod +x deploy.sh
./deploy.sh

脚本会自动完成:

  1. 检查 Docker 环境
  2. 拉取最新代码(如果在 git 仓库中)
  3. 构建前端静态资源FRONTEND_DIST_PATH(Docker 内 Node 或宿主机 pnpm,见 .env
  4. 后端镜像:默认 docker compose build backend;若 BACKEND_PULL_ONLY=1pull 已推送的 BACKEND_IMAGE
  5. docker compose up -d mysql redis backend
  6. 打印服务状态与宝塔后续步骤提示

4.6 配置 HTTPS

bash
sudo apt install certbot python3-certbot-nginx
sudo certbot --nginx -d your-domain.com

Certbot 会自动修改 Nginx 配置并安装证书,证书自动续期。


5. 验证部署

bash
# 查看容器状态(应全部为 Up / healthy)
docker compose -f docker-compose.prod.yml ps

# 直接探活后端(根路径 /health,不经 /api/v1 前缀)
curl -sS http://127.0.0.1:8080/health

# 经域名(宝塔已反代 api 子域到 8080 时)
curl -sS https://api.your-domain.com/health

# 浏览器访问前端站点
https://your-domain.com

6. 日常运维

查看日志

bash
cd deploy

# 后端日志
docker compose -f docker-compose.prod.yml logs -f backend

# MySQL 日志
docker compose -f docker-compose.prod.yml logs -f mysql

# 全部日志
docker compose -f docker-compose.prod.yml logs -f

更新部署

bash
cd deploy
git -C .. pull
./deploy.sh

脚本会重新构建前端静态、按需构建或拉取后端镜像并滚动重启相关容器。

重启单个服务

bash
docker compose -f docker-compose.prod.yml restart backend

(默认 compose Nginx 容器;Web 服务器日志在宝塔面板查看。)

停止 / 启动

bash
# 停止所有服务(保留数据)
docker compose -f docker-compose.prod.yml down

# 启动
docker compose -f docker-compose.prod.yml up -d

# 停止并删除所有数据卷(⚠️ 慎用!不可恢复)
docker compose -f docker-compose.prod.yml down -v

数据库备份

bash
# 备份
docker exec shice-mysql mysqldump -u root -p<MYSQL_ROOT_PASSWORD> shice > backup_$(date +%Y%m%d).sql

# 恢复
docker exec -i shice-mysql mysql -u root -p<MYSQL_ROOT_PASSWORD> shice < backup_20260412.sql

进入容器调试

bash
# 进入后端容器
docker exec -it shice-backend sh

# 进入 MySQL
docker exec -it shice-mysql mysql -u shice -p shice

# 进入 Redis
docker exec -it shice-redis redis-cli

7. Nginx 配置说明

默认生产:Nginx 跑在宝塔宿主机上,可参考 deploy/nginx/baota-*.conf 与 README 中的 location 示例。default.conf 描述的是「单 Nginx 同时反代前后端」的参考写法(上游可能是 127.0.0.1:8080 或 Docker 网络中的 backend:8080,取决于你是否全容器化)。

deploy/nginx/default.conf 的关键配置(摘录):

路由行为
/ 前端 SPA,try_files 回退到 index.html
/api/反代到 backend:8080,关闭 proxy_buffering 以支持 SSE
/health后端健康检查
静态资源 *.js, *.css缓存 30 天,Cache-Control: public, immutable

SSE 流式对话需要 Nginx 关闭代理缓冲:

nginx
proxy_buffering off;
proxy_cache off;
proxy_read_timeout 300s;
chunked_transfer_encoding on;

8. 安全清单

  • [ ] .env 中所有密码改为强随机值
  • [ ] JWT_SECRET 使用 openssl rand -hex 32 生成
  • [ ] AI_API_KEY 通过环境变量注入,不提交到 git
  • [ ] config.prod.yamlserver.mode: release
  • [ ] config.prod.yamlallow_mock_purchase: false
  • [ ] MySQL / Redis 端口不对外暴露(生产 compose 已默认不映射)
  • [ ] 开启 UFW 防火墙,仅放行 22 / 80 / 443
  • [ ] 配置 HTTPS(Let's Encrypt)
  • [ ] 定期备份数据库
  • [ ] .env 文件权限设为 600
bash
# 防火墙设置
sudo ufw allow 22
sudo ufw allow 80
sudo ufw allow 443
sudo ufw enable

# 限制 .env 权限
chmod 600 deploy/.env

9. 开发环境

开发环境只需启动基础设施容器,前后端在本地运行:

bash
# 启动 MySQL + Redis + Qdrant + MinIO
cd deploy && docker-compose up -d

# 配置后端
cp backend/config.example.yaml backend/config.yaml
# 编辑 config.yaml,填入数据库密码和 AI API Key

# 启动后端
cd backend && go run ./cmd/server

# 启动前端 Web
cd frontend && pnpm install && pnpm dev:web

# 可选:Electron 壳(会再起 Vite 于 3000,勿与已有 dev:web 重复占用端口)
cd frontend && pnpm dev:desktop
服务地址
前端http://localhost:3000
Electron 开发同上(Electron 加载 Vite);生产包见 frontend/apps/desktop
后端 APIhttp://localhost:8080
MySQLlocalhost:3306
Redislocalhost:6379
Qdrantlocalhost:6333
MinIO 控制台localhost:9001

10. 故障排查

症状排查
容器启动失败docker compose logs <服务名> 查看错误日志
后端连不上 MySQL检查 config.prod.yaml 中 DSN 密码是否与 .env 一致
前端白屏deploy.sh 是否成功;检查 FRONTEND_DIST_PATH 下是否有 index.html / assets;浏览器控制台是否 404;VITE_API_BASE_URL 是否指向正确 API
SSE 流式不工作确认 Nginx proxy_buffering off;检查是否有 CDN 缓冲
HTTPS 证书过期sudo certbot renew(通常自动续期)
数据库表缺少新字段后端启动时 GORM AutoMigrate 会自动添加新列;或手动执行 init.sql
AI 返回空 / 报错检查 AI_API_KEY 是否有效、额度是否充足