feat: production branch with deploy config for baota panel

- Add deploy/ directory with production env, supervisor, nginx, migration configs
- Include all latest features: admin management, feedback, footer with ICP/beian
- Database: foreign_trade (PostgreSQL), user: foreign_trade
- Frontend: trade.yuzhiran.com, backend proxy via Nginx
This commit is contained in:
TradeMate Dev
2026-05-14 09:19:30 +08:00
parent 23a31f7c00
commit 5a1af9f82f
15 changed files with 1377 additions and 71 deletions
+105
View File
@@ -0,0 +1,105 @@
# 生产部署文档(宝塔面板)
## 前提条件
宝塔面板已安装:
- Nginx
- PostgreSQL(已有数据库 `foreign_trade`
- Redis
- Python 3.11+
## 目录结构(宝塔站点根目录)
```
/www/wwwroot/trade.yuzhiran.com/
├── backend/ # FastAPI 后端代码
│ ├── .env # 生产环境变量
│ ├── app/
│ ├── alembic/
│ └── ...
├── frontend/ # 前端静态文件
│ └── dist/ # uni-app 构建产物
└── deploy/ # 部署配置(此目录)
```
## 部署步骤
### 1. 上传代码到服务器
将项目代码(production 分支)上传到 `/www/wwwroot/trade.yuzhiran.com/`
### 2. 配置后端环境变量
```bash
cp deploy/backend/.env.production backend/.env
# 编辑 backend/.env,填入:
# - SECRET_KEY(随机字符串,用于 JWT 签名)
# - AI API KeyOPENAI_API_KEY 或 SENSENOVA_API_KEY 等)
vim backend/.env
```
### 3. 安装后端依赖 & 运行迁移
```bash
cd backend
python3 -m venv venv
source venv/bin/activate
pip install -r requirements.txt
alembic upgrade head
```
### 4. 构建前端
```bash
cd uni-app
npm install
npm run build:h5
# 产物在 dist/build/h5/ 目录
# 将 dist/build/h5/ 下的内容复制到 /www/wwwroot/trade.yuzhiran.com/frontend/dist/
```
### 5. 配置 Nginx(宝塔面板操作)
在宝塔面板中:
1. 添加站点 `trade.yuzhiran.com`
2. 站点根目录设为 `/www/wwwroot/trade.yuzhiran.com/frontend/dist`
3. 修改 Nginx 配置,参考 `deploy/frontend/nginx.conf`
关键配置点:
- 根目录指向前端 dist
- `/api/` 反向代理到 `http://127.0.0.1:8000`
- SPA fallback: `try_files $uri $uri/ /index.html`
### 6. 启动后端(宝塔 Python 项目管理器)
在宝塔面板中使用 **Python项目管理器**
- 项目路径:`/www/wwwroot/trade.yuzhiran.com/backend`
- Python 版本:3.11
- 启动命令:`uvicorn app.main:app --host 0.0.0.0 --port 8000 --workers 2`
- 项目名称:`trademate-backend`
或者使用 Supervisor 命令行部署:
```bash
pip install supervisor
supervisord -c deploy/backend/supervisord.conf
```
### 7. 验证
- 访问 https://trade.yuzhiran.com → 前端正常加载
- 访问 https://trade.yuzhiran.com/api/health → 返回 `{"status": "ok"}`
## 常见问题
**Q: 数据库迁移失败?**
A: 确认 PostgreSQL 中 `foreign_trade` 数据库已创建,用户有权限。
```sql
CREATE DATABASE foreign_trade;
GRANT ALL PRIVILEGES ON DATABASE foreign_trade TO foreign_trade;
```
**Q: 前端 API 请求 502**
A: 检查后端是否启动,以及 Nginx 中 `/api/` 的 proxy_pass 地址是否正确。
**Q: CORS 报错?**
A: 确认 `backend/.env` 中的 `FRONTEND_URL` 与实际前端域名一致。
+59
View File
@@ -0,0 +1,59 @@
# 生产环境配置(基于宝塔面板 PostgreSQL foreign_trade 数据库)
APP_NAME=TradeMate
SECRET_KEY=change-this-to-a-random-secret-key
JWT_ALGORITHM=HS256
ACCESS_TOKEN_EXPIRE_MINUTES=60
REFRESH_TOKEN_EXPIRE_DAYS=30
# 数据库(foreign_trade
DATABASE_URL=postgresql+asyncpg://foreign_trade:dWFNi67nHNbPbjmP@localhost:5432/foreign_trade
# Redis(宝塔自带,默认端口)
REDIS_URL=redis://localhost:6379/0
# Celery
CELERY_BROKER_URL=redis://localhost:6379/1
CELERY_RESULT_BACKEND=redis://localhost:6379/2
# AI 提供商(按需填入)
OPENAI_API_KEY=
ANTHROPIC_API_KEY=
DEEPL_API_KEY=
SENSENOVA_API_KEY=
SENSENOVA_BASE_URL=https://token.sensenova.cn/v1
SENSENOVA_MODEL=sensenova-6.7-flash-lite
IFLYTEK_API_KEY=
IFLYTEK_API_BASE=https://maas-api.cn-huabei-1.xf-yun.com/v2
IFLYTEK_MODEL=astron-code-latest
LOCAL_MODEL_ENABLED=false
LOCAL_MODEL_URL=http://localhost:8001
# WhatsApp Cloud API
WHATSAPP_API_TOKEN=
WHATSAPP_PHONE_NUMBER_ID=
WHATSAPP_WEBHOOK_VERIFY_TOKEN=
# 微信
WECHAT_APP_ID=
WECHAT_APP_SECRET=
# 汇率 API
EXCHANGE_RATE_API_KEY=
# 文件存储
UPLOAD_DIR=./uploads
MAX_UPLOAD_SIZE=10485760
# 错误监控 (Sentry)
SENTRY_DSN=
DEBUG=false
# URL(以宝塔实际域名/端口为准)
FRONTEND_URL=https://trade.yuzhiran.com
BACKEND_URL=https://api.trade.yuzhiran.com
# 数据库调试关闭
DB_ECHO=false
+13
View File
@@ -0,0 +1,13 @@
[program:trademate-backend]
command=/www/server/panel/pyenv/bin/uvicorn app.main:app --host 0.0.0.0 --port 8000 --workers 2 --proxy-headers --forwarded-allow-ips='*'
directory=/www/wwwroot/trade.yuzhiran.com/backend
user=www
autostart=true
autorestart=true
stopasgroup=true
killasgroup=true
stdout_logfile=/www/wwwlogs/trademate-backend.log
stderr_logfile=/www/wwwlogs/trademate-backend.error.log
stdout_logfile_maxbytes=50MB
stderr_logfile_maxbytes=50MB
environment=PATH="/www/server/panel/pyenv/bin:/usr/local/bin:/usr/bin:/bin",HOME="/home/www"
+29
View File
@@ -0,0 +1,29 @@
#!/bin/bash
# 生产数据库迁移脚本
# 使用方式: bash deploy/database/migrate.sh
# 注意:需先在 backend/ 目录下配置好 .env 或设置好环境变量
set -e
cd "$(dirname "$0")/../../backend"
# 检查 .env 是否存在
if [ ! -f ".env" ]; then
echo "❌ 未找到 .env 文件,请先复制 deploy/backend/.env.production 到 backend/.env"
echo " cp deploy/backend/.env.production backend/.env"
echo " 然后编辑 .env 填入 SECRET_KEY 和 AI API Key"
exit 1
fi
echo "🔧 激活虚拟环境..."
if [ -d "venv" ]; then
source venv/bin/activate
fi
echo "📦 安装/更新依赖..."
pip install -r requirements.txt -q
echo "🗄️ 运行数据库迁移..."
alembic upgrade head
echo "✅ 迁移完成"
+70
View File
@@ -0,0 +1,70 @@
# 宝塔面板 Nginx 配置
# 注意:请勿直接覆盖宝塔生成的配置文件!
# 将此配置中的 server 块复制到宝塔对应站点的配置中
# 宝塔路径: /www/server/panel/vhost/nginx/trade.yuzhiran.com.conf
server {
listen 80;
server_name trade.yuzhiran.com;
return 301 https://$host$request_uri;
}
server {
listen 443 ssl http2;
server_name trade.yuzhiran.com;
# SSL 证书(宝塔面板中配置,或取消注释以下行)
# ssl_certificate /www/server/panel/vhost/cert/trade.yuzhiran.com/fullchain.pem;
# ssl_certificate_key /www/server/panel/vhost/cert/trade.yuzhiran.com/privkey.pem;
# ssl_protocols TLSv1.1 TLSv1.2 TLSv1.3;
# ssl_ciphers EECDH+CHACHA20:EECDH+CHACHA20-draft:EECDH+AES128:RSA+AES128:EECDH+AES256:RSA+AES256:EECDH+3DES:RSA+3DES:!MD5;
# ssl_prefer_server_ciphers on;
# 前端静态文件(uni-app build:h5 产物)
root /www/wwwroot/trade.yuzhiran.com/frontend/dist;
index index.html;
# gzip
gzip on;
gzip_min_length 1k;
gzip_comp_level 6;
gzip_types text/plain text/css text/javascript application/json application/javascript image/svg+xml;
# API 反向代理到后端
location /api/ {
proxy_pass http://127.0.0.1:8000;
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;
proxy_read_timeout 120s;
proxy_send_timeout 120s;
# WebSocket 支持(如有需要)
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
}
# 上传文件(如有需要可配置单独的路径)
# location /uploads/ {
# alias /www/wwwroot/trade.yuzhiran.com/backend/uploads/;
# expires 7d;
# }
# SPA 路由 fallback
location / {
try_files $uri $uri/ /index.html;
}
# 静态资源缓存
location ~* \.(js|css|png|jpg|jpeg|gif|ico|svg|woff|woff2|ttf|eot)$ {
expires 30d;
add_header Cache-Control "public, immutable";
}
# 禁止访问隐藏文件
location ~ /\. {
deny all;
}
}