修复bug

This commit is contained in:
dekun
2026-05-28 21:47:42 +08:00
parent 1d5c97904f
commit 7880a92af3
4 changed files with 346 additions and 332 deletions
+13
View File
@@ -0,0 +1,13 @@
# Shell 脚本强制 LF,避免 Linux 部署报错
*.sh text eol=lf
# 配置文件
*.cjs text eol=lf
*.js text eol=lf
*.json text eol=lf
*.md text eol=lf
*.sql text eol=lf
*.py text eol=lf
*.vue text eol=lf
*.css text eol=lf
*.html text eol=lf
+194 -193
View File
@@ -1,193 +1,194 @@
# 部署文档 # 部署文档
> 代码仓库:[https://git.bz121.com/dekun/crypto-pre-trade-system.git](https://git.bz121.com/dekun/crypto-pre-trade-system.git) > 代码仓库:[https://git.bz121.com/dekun/crypto-pre-trade-system.git](https://git.bz121.com/dekun/crypto-pre-trade-system.git)
本文档说明如何在 **Ubuntu 服务器**上使用 **PM2** 守护进程部署本系统。 本文档说明如何在 **Ubuntu 服务器**上使用 **PM2** 守护进程部署本系统。
--- ---
## 部署环境要求 ## 部署环境要求
| 项目 | 要求 | | 项目 | 要求 |
|------|------| |------|------|
| 操作系统 | Ubuntu 20.04 / 22.04 / 24.04 | | 操作系统 | Ubuntu 20.04 / 22.04 / 24.04 |
| 运行用户 | root | | 运行用户 | root |
| 安装路径 | `/opt/crypto-pre-trade-system` | | 安装路径 | `/opt/crypto-pre-trade-system` |
| 进程守护 | PM2 | | 进程守护 | PM2 |
| Python | 3.10+(虚拟环境) | | Python | 3.10+(虚拟环境) |
| Node.js | 18+(仅构建前端时使用) | | Node.js | 18+(仅构建前端时使用) |
| 访问端口 | **1125** | | 访问端口 | **1125** |
--- ---
## 一键部署(推荐) ## 一键部署(推荐)
**root** 用户登录服务器,执行: **root** 用户登录服务器,执行:
```bash ```bash
# 首次部署:克隆仓库并运行安装脚本 # 首次部署:克隆仓库并运行安装脚本
git clone https://git.bz121.com/dekun/crypto-pre-trade-system.git /opt/crypto-pre-trade-system git clone https://git.bz121.com/dekun/crypto-pre-trade-system.git /opt/crypto-pre-trade-system
cd /opt/crypto-pre-trade-system cd /opt/crypto-pre-trade-system
bash deploy/install.sh bash deploy/install.sh
``` ```
脚本会自动完成: 脚本会自动完成:
1. 安装系统依赖(git、python3、nodejs、pm2 1. 安装系统依赖(git、python3、nodejs、pm2
2. 创建 Python 虚拟环境并安装后端依赖 2. 创建 Python 虚拟环境并安装后端依赖
3. 构建前端静态资源 3. 构建前端静态资源
4. 通过 PM2 启动服务并设置开机自启 4. 通过 PM2 启动服务并设置开机自启
5. 执行健康检查 5. 执行健康检查
部署完成后访问:**http://\<服务器IP\>:1125** 部署完成后访问:**http://\<服务器IP\>:1125**
--- ---
## 更新部署 ## 更新部署
代码有更新时,在服务器上重新执行安装脚本即可: 代码有更新时,在服务器上重新执行安装脚本即可:
```bash ```bash
cd /opt/crypto-pre-trade-system cd /opt/crypto-pre-trade-system
bash deploy/install.sh bash deploy/install.sh
``` ```
脚本会自动 `git pull`、重新构建前端、重启 PM2 进程。 脚本会自动 `git pull`、重新构建前端、重启 PM2 进程。
--- ---
## 手动部署步骤 ## 手动部署步骤
若需手动逐步部署,按以下步骤操作: 若需手动逐步部署,按以下步骤操作:
### 1. 克隆仓库 ### 1. 克隆仓库
```bash ```bash
git clone https://git.bz121.com/dekun/crypto-pre-trade-system.git /opt/crypto-pre-trade-system git clone https://git.bz121.com/dekun/crypto-pre-trade-system.git /opt/crypto-pre-trade-system
cd /opt/crypto-pre-trade-system cd /opt/crypto-pre-trade-system
``` ```
### 2. 安装系统依赖 ### 2. 安装系统依赖
```bash ```bash
apt-get update apt-get update
apt-get install -y git python3 python3-venv python3-pip curl apt-get install -y git python3 python3-venv python3-pip curl
# Node.js 20 # Node.js 20
curl -fsSL https://deb.nodesource.com/setup_20.x | bash - curl -fsSL https://deb.nodesource.com/setup_20.x | bash -
apt-get install -y nodejs apt-get install -y nodejs
# PM2 # PM2
npm install -g pm2 npm install -g pm2
``` ```
### 3. 后端虚拟环境 ### 3. 后端虚拟环境
```bash ```bash
cd /opt/crypto-pre-trade-system/backend cd /opt/crypto-pre-trade-system/backend
python3 -m venv venv python3 -m venv venv
venv/bin/pip install -r requirements.txt venv/bin/pip install -r requirements.txt
mkdir -p data mkdir -p data
``` ```
### 4. 构建前端 ### 4. 构建前端
```bash ```bash
cd /opt/crypto-pre-trade-system/frontend cd /opt/crypto-pre-trade-system/frontend
npm install npm install
npm run build npm run build
``` ```
### 5. PM2 启动 ### 5. PM2 启动
```bash ```bash
cd /opt/crypto-pre-trade-system cd /opt/crypto-pre-trade-system
mkdir -p logs mkdir -p logs
pm2 start ecosystem.config.cjs pm2 start ecosystem.config.cjs
pm2 save pm2 save
pm2 startup systemd -u root --hp /root pm2 startup systemd -u root --hp /root
``` ```
--- ---
## PM2 常用命令 ## PM2 常用命令
```bash ```bash
pm2 status # 查看进程状态 pm2 status # 查看进程状态
pm2 logs crypto-pre-trade # 查看实时日志 pm2 logs crypto-pre-trade # 查看实时日志
pm2 restart crypto-pre-trade # 重启服务 pm2 restart crypto-pre-trade # 重启服务
pm2 stop crypto-pre-trade # 停止服务 pm2 stop crypto-pre-trade # 停止服务
pm2 delete crypto-pre-trade # 删除进程 pm2 delete crypto-pre-trade # 删除进程
``` ```
日志文件位置: 日志文件位置:
- 标准输出:`/opt/crypto-pre-trade-system/logs/pm2-out.log` - 标准输出:`/opt/crypto-pre-trade-system/logs/pm2-out.log`
- 错误输出:`/opt/crypto-pre-trade-system/logs/pm2-error.log` - 错误输出:`/opt/crypto-pre-trade-system/logs/pm2-error.log`
--- ---
## 架构说明 ## 架构说明
生产环境采用 **单进程单端口** 模式: 生产环境采用 **单进程单端口** 模式:
``` ```
PM2 → uvicorn (0.0.0.0:1125) PM2 → uvicorn (0.0.0.0:1125)
├── /api/* → FastAPI 后端接口 ├── /api/* → FastAPI 后端接口
└── /* → Vue3 前端静态资源(frontend/dist └── /* → Vue3 前端静态资源(frontend/dist
``` ```
- 前端构建产物由 FastAPI 直接托管,无需额外 Nginx - 前端构建产物由 FastAPI 直接托管,无需额外 Nginx
- SQLite 数据库文件:`/opt/crypto-pre-trade-system/backend/data/pretrade.db` - SQLite 数据库文件:`/opt/crypto-pre-trade-system/backend/data/pretrade.db`
- 重启服务不丢失数据 - 重启服务不丢失数据
--- ---
## 防火墙 ## 防火墙
若服务器开启了防火墙,需放行 1125 端口: 若服务器开启了防火墙,需放行 1125 端口:
```bash ```bash
# ufw # ufw
ufw allow 1125/tcp ufw allow 1125/tcp
# firewalld # firewalld
firewall-cmd --permanent --add-port=1125/tcp firewall-cmd --permanent --add-port=1125/tcp
firewall-cmd --reload firewall-cmd --reload
``` ```
--- ---
## 重置数据库 ## 重置数据库
```bash ```bash
pm2 stop crypto-pre-trade pm2 stop crypto-pre-trade
rm /opt/crypto-pre-trade-system/backend/data/pretrade.db rm /opt/crypto-pre-trade-system/backend/data/pretrade.db
pm2 start crypto-pre-trade pm2 start crypto-pre-trade
``` ```
重启后系统自动重建表结构并写入默认数据。 重启后系统自动重建表结构并写入默认数据。
--- ---
## 故障排查 ## 故障排查
| 现象 | 排查方式 | | 现象 | 排查方式 |
|------|---------| |------|---------|
| 无法访问 | `pm2 status` 确认进程 online`curl http://127.0.0.1:1125/api/health` | | `$'\r': command not found` | Windows 换行符问题,执行 `sed -i 's/\r$//' deploy/install.sh` 后重试 |
| 502 / 连接拒绝 | 检查防火墙是否放行 1125 端口 | | 无法访问 | `pm2 status` 确认进程 online`curl http://127.0.0.1:1125/api/health` |
| 前端白屏 | 确认 `frontend/dist` 存在;重新 `npm run build` | | 502 / 连接拒绝 | 检查防火墙是否放行 1125 端口 |
| API 报错 | `pm2 logs crypto-pre-trade --lines 50` | | 前端白屏 | 确认 `frontend/dist` 存在;重新 `npm run build` |
| 数据库问题 | 检查 `backend/data/` 目录权限 | | API 报错 | `pm2 logs crypto-pre-trade --lines 50` |
| 数据库问题 | 检查 `backend/data/` 目录权限 |
---
---
## 本地开发 vs 生产部署
## 本地开发 vs 生产部署
| | 本地开发 | 生产部署 |
|---|---------|---------| | | 本地开发 | 生产部署 |
| 后端 | `uvicorn --reload --port 8000` | PM2 + uvicorn `:1125` | |---|---------|---------|
| 端 | `npm run dev :1125`(代理到 8000 | `npm run build`,由 FastAPI 托管 | | 端 | `uvicorn --reload --port 8000` | PM2 + uvicorn `:1125` |
| 访问 | http://localhost:1125 | http://\<服务器IP\>:1125 | | 前端 | `npm run dev :1125`(代理到 8000 | `npm run build`,由 FastAPI 托管 |
| 访问 | http://localhost:1125 | http://\<服务器IP\>:1125 |
本地开发说明见 [README.md](./README.md)。
本地开发说明见 [README.md](./README.md)。
+113 -113
View File
@@ -1,113 +1,113 @@
#!/bin/bash #!/bin/bash
# ============================================================ # ============================================================
# 加密货币前置匹配系统 — Ubuntu 一键部署脚本 # 加密货币前置匹配系统 — Ubuntu 一键部署脚本
# 仓库:https://git.bz121.com/dekun/crypto-pre-trade-system.git # 仓库:https://git.bz121.com/dekun/crypto-pre-trade-system.git
# 部署路径:/opt/crypto-pre-trade-system # 部署路径:/opt/crypto-pre-trade-system
# 运行用户:root # 运行用户:root
# 进程守护:PM2 # 进程守护:PM2
# 访问端口:1125 # 访问端口:1125
# ============================================================ # ============================================================
set -euo pipefail set -euo pipefail
REPO_URL="https://git.bz121.com/dekun/crypto-pre-trade-system.git" REPO_URL="https://git.bz121.com/dekun/crypto-pre-trade-system.git"
INSTALL_DIR="/opt/crypto-pre-trade-system" INSTALL_DIR="/opt/crypto-pre-trade-system"
PORT=1125 PORT=1125
RED='\033[0;31m' RED='\033[0;31m'
GREEN='\033[0;32m' GREEN='\033[0;32m'
YELLOW='\033[1;33m' YELLOW='\033[1;33m'
NC='\033[0m' NC='\033[0m'
log() { echo -e "${GREEN}[INFO]${NC} $*"; } log() { echo -e "${GREEN}[INFO]${NC} $*"; }
warn() { echo -e "${YELLOW}[WARN]${NC} $*"; } warn() { echo -e "${YELLOW}[WARN]${NC} $*"; }
err() { echo -e "${RED}[ERROR]${NC} $*"; exit 1; } err() { echo -e "${RED}[ERROR]${NC} $*"; exit 1; }
# ── 检查 root 权限 ── # ── 检查 root 权限 ──
if [ "$(id -u)" -ne 0 ]; then if [ "$(id -u)" -ne 0 ]; then
err "请使用 root 用户运行:sudo bash deploy/install.sh" err "请使用 root 用户运行:sudo bash deploy/install.sh"
fi fi
log "========== 开始部署 crypto-pre-trade-system ==========" log "========== 开始部署 crypto-pre-trade-system =========="
# ── 1. 安装系统依赖 ── # ── 1. 安装系统依赖 ──
log "安装系统依赖..." log "安装系统依赖..."
export DEBIAN_FRONTEND=noninteractive export DEBIAN_FRONTEND=noninteractive
apt-get update -qq apt-get update -qq
apt-get install -y -qq git curl python3 python3-venv python3-pip apt-get install -y -qq git curl python3 python3-venv python3-pip
# Node.js 18+(若未安装) # Node.js 18+(若未安装)
if ! command -v node &>/dev/null; then if ! command -v node &>/dev/null; then
log "安装 Node.js 20 LTS..." log "安装 Node.js 20 LTS..."
curl -fsSL https://deb.nodesource.com/setup_20.x | bash - curl -fsSL https://deb.nodesource.com/setup_20.x | bash -
apt-get install -y -qq nodejs apt-get install -y -qq nodejs
fi fi
# PM2(若未安装) # PM2(若未安装)
if ! command -v pm2 &>/dev/null; then if ! command -v pm2 &>/dev/null; then
log "安装 PM2..." log "安装 PM2..."
npm install -g pm2 npm install -g pm2
fi fi
log "Node $(node -v) | Python $(python3 --version) | PM2 $(pm2 -v)" log "Node $(node -v) | Python $(python3 --version) | PM2 $(pm2 -v)"
# ── 2. 拉取代码 ── # ── 2. 拉取代码 ──
if [ -d "$INSTALL_DIR/.git" ]; then if [ -d "$INSTALL_DIR/.git" ]; then
log "更新代码..." log "更新代码..."
cd "$INSTALL_DIR" cd "$INSTALL_DIR"
git pull origin main 2>/dev/null || git pull origin master 2>/dev/null || git pull git pull origin main 2>/dev/null || git pull origin master 2>/dev/null || git pull
else else
log "克隆仓库..." log "克隆仓库..."
git clone "$REPO_URL" "$INSTALL_DIR" git clone "$REPO_URL" "$INSTALL_DIR"
cd "$INSTALL_DIR" cd "$INSTALL_DIR"
fi fi
# ── 3. 创建日志目录 ── # ── 3. 创建日志目录 ──
mkdir -p "$INSTALL_DIR/logs" mkdir -p "$INSTALL_DIR/logs"
mkdir -p "$INSTALL_DIR/backend/data" mkdir -p "$INSTALL_DIR/backend/data"
# ── 4. Python 虚拟环境 + 依赖 ── # ── 4. Python 虚拟环境 + 依赖 ──
log "配置 Python 虚拟环境..." log "配置 Python 虚拟环境..."
cd "$INSTALL_DIR/backend" cd "$INSTALL_DIR/backend"
if [ ! -d "venv" ]; then if [ ! -d "venv" ]; then
python3 -m venv venv python3 -m venv venv
fi fi
venv/bin/pip install -q --upgrade pip venv/bin/pip install -q --upgrade pip
venv/bin/pip install -q -r requirements.txt venv/bin/pip install -q -r requirements.txt
# ── 5. 构建前端 ── # ── 5. 构建前端 ──
log "构建前端..." log "构建前端..."
cd "$INSTALL_DIR/frontend" cd "$INSTALL_DIR/frontend"
npm install --silent npm install --silent
npm run build npm run build
# ── 6. PM2 启动 / 重启 ── # ── 6. PM2 启动 / 重启 ──
log "启动 PM2 守护进程..." log "启动 PM2 守护进程..."
cd "$INSTALL_DIR" cd "$INSTALL_DIR"
pm2 delete crypto-pre-trade 2>/dev/null || true pm2 delete crypto-pre-trade 2>/dev/null || true
pm2 start ecosystem.config.cjs pm2 start ecosystem.config.cjs
pm2 save pm2 save
# 设置 PM2 开机自启(已配置则跳过) # 设置 PM2 开机自启(已配置则跳过)
pm2 startup systemd -u root --hp /root 2>/dev/null | tail -1 | bash 2>/dev/null || true pm2 startup systemd -u root --hp /root 2>/dev/null | tail -1 | bash 2>/dev/null || true
# ── 7. 健康检查 ── # ── 7. 健康检查 ──
log "等待服务启动..." log "等待服务启动..."
sleep 3 sleep 3
if curl -sf "http://127.0.0.1:${PORT}/api/health" > /dev/null; then if curl -sf "http://127.0.0.1:${PORT}/api/health" > /dev/null; then
log "健康检查通过" log "健康检查通过"
else else
warn "健康检查未通过,请查看日志:pm2 logs crypto-pre-trade" warn "健康检查未通过,请查看日志:pm2 logs crypto-pre-trade"
fi fi
echo "" echo ""
log "========== 部署完成 ==========" log "========== 部署完成 =========="
echo -e " 访问地址:${GREEN}http://<服务器IP>:${PORT}${NC}" echo -e " 访问地址:${GREEN}http://<服务器IP>:${PORT}${NC}"
echo -e " API 文档:${GREEN}http://<服务器IP>:${PORT}/docs${NC}" echo -e " API 文档:${GREEN}http://<服务器IP>:${PORT}/docs${NC}"
echo -e " 安装目录:${INSTALL_DIR}" echo -e " 安装目录:${INSTALL_DIR}"
echo -e " 常用命令:" echo -e " 常用命令:"
echo -e " pm2 status # 查看状态" echo -e " pm2 status # 查看状态"
echo -e " pm2 logs crypto-pre-trade # 查看日志" echo -e " pm2 logs crypto-pre-trade # 查看日志"
echo -e " pm2 restart crypto-pre-trade # 重启服务" echo -e " pm2 restart crypto-pre-trade # 重启服务"
echo -e " bash deploy/install.sh # 更新并重新部署" echo -e " bash deploy/install.sh # 更新并重新部署"
echo "" echo ""
+26 -26
View File
@@ -1,26 +1,26 @@
/** /**
* PM2 进程配置 * PM2 进程配置
* 部署路径:/opt/crypto-pre-trade-system * 部署路径:/opt/crypto-pre-trade-system
* 运行用户:root * 运行用户:root
* 访问端口:1125 * 访问端口:1125
*/ */
module.exports = { module.exports = {
apps: [ apps: [
{ {
name: 'crypto-pre-trade', name: 'crypto-pre-trade',
cwd: '/opt/crypto-pre-trade-system/backend', cwd: '/opt/crypto-pre-trade-system/backend',
script: 'venv/bin/uvicorn', script: 'venv/bin/uvicorn',
args: 'app.main:app --host 0.0.0.0 --port 1125', args: 'app.main:app --host 0.0.0.0 --port 1125',
interpreter: 'none', interpreter: 'none',
autorestart: true, autorestart: true,
watch: false, watch: false,
max_memory_restart: '300M', max_memory_restart: '300M',
env: { env: {
NODE_ENV: 'production', NODE_ENV: 'production',
}, },
error_file: '/opt/crypto-pre-trade-system/logs/pm2-error.log', error_file: '/opt/crypto-pre-trade-system/logs/pm2-error.log',
out_file: '/opt/crypto-pre-trade-system/logs/pm2-out.log', out_file: '/opt/crypto-pre-trade-system/logs/pm2-out.log',
log_date_format: 'YYYY-MM-DD HH:mm:ss', log_date_format: 'YYYY-MM-DD HH:mm:ss',
}, },
], ],
}; };