2026-04-12 09:49:18 +08:00
|
|
|
|
# 甲辰藏品管理系统 部署手册
|
|
|
|
|
|
|
2026-04-12 14:24:48 +08:00
|
|
|
|
**当前版本:v1.2.88**
|
|
|
|
|
|
|
|
|
|
|
|
---
|
|
|
|
|
|
|
2026-04-12 09:49:18 +08:00
|
|
|
|
## 环境概览
|
|
|
|
|
|
|
|
|
|
|
|
### 服务器信息
|
|
|
|
|
|
|
|
|
|
|
|
| 环境 | 前端 | 后端 | SSH密码 |
|
|
|
|
|
|
|------|------|------|--------|
|
|
|
|
|
|
| **D测试环境** | 114.55.137.168, 172.26.30.32 (内网) | 47.111.184.210, 172.26.30.33 (内网) | Jiachend123 |
|
|
|
|
|
|
| **101生产环境** | 47.98.171.101 (80端口) | 47.98.171.101:8080 | Coolbot123 |
|
|
|
|
|
|
|
|
|
|
|
|
### 数据库信息
|
|
|
|
|
|
|
|
|
|
|
|
| 用途 | 数据库 | 地址 | 端口 | 用户名 | 密码 |
|
|
|
|
|
|
|------|--------|------|------|--------|------|
|
|
|
|
|
|
| **主数据库** | jiachenlong | pgm-bp1t5w248t7s1pvr.pg.rds.aliyuncs.com | 5432 | jiachenlong | Passwd1@3 |
|
|
|
|
|
|
| **一尘数据库** | coolbot_data | pgm-bp1t1008h019ez6c.pg.rds.aliyuncs.com | 5432 | coolbot | Coolbot123 |
|
|
|
|
|
|
|
2026-04-12 14:24:48 +08:00
|
|
|
|
> ⚠️ **密码中的特殊字符 `@` 必须URL编码为 `%40`**
|
|
|
|
|
|
> - `Passwd1@3` → `Passwd1%403`
|
|
|
|
|
|
> - `Coolbot123` 无需编码
|
|
|
|
|
|
|
2026-04-12 09:49:18 +08:00
|
|
|
|
### OSS存储
|
|
|
|
|
|
- Bucket: jiachenlong-oss
|
|
|
|
|
|
|
|
|
|
|
|
---
|
|
|
|
|
|
|
2026-04-12 14:24:48 +08:00
|
|
|
|
## 环境变量 (.env)
|
|
|
|
|
|
|
|
|
|
|
|
> 📁 完整示例见 `backend/.env.example`
|
|
|
|
|
|
|
|
|
|
|
|
### 数据库配置
|
|
|
|
|
|
```env
|
|
|
|
|
|
# 主数据库 - jiachenlong
|
|
|
|
|
|
DATABASE_URL=postgresql://jiachenlong:Passwd1%403@pgm-bp1t5w248t7s1pvr.pg.rds.aliyuncs.com:5432/jiachenlong
|
|
|
|
|
|
|
|
|
|
|
|
# 一尘数据库 - coolbot_data
|
|
|
|
|
|
COOLBOT_DB_URL=postgresql://coolbot:Coolbot123@pgm-bp1t1008h019ez6c.pg.rds.aliyuncs.com:5432/coolbot_data
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### JWT认证配置
|
|
|
|
|
|
```env
|
|
|
|
|
|
SECRET_KEY=jiachenlong-production-secret-key-2026
|
|
|
|
|
|
ALGORITHM=HS256
|
|
|
|
|
|
ACCESS_TOKEN_EXPIRE_MINUTES=10080
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 阿里云百炼AI (DASHSCOPE)
|
|
|
|
|
|
```env
|
|
|
|
|
|
# 用于AI批量解析藏品行情数据
|
|
|
|
|
|
DASHSCOPE_API_KEY=your-dashscope-api-key
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 阿里云OSS存储
|
|
|
|
|
|
```env
|
|
|
|
|
|
OSS_ACCESS_KEY_ID=your-oss-access-key-id
|
|
|
|
|
|
OSS_ACCESS_KEY_SECRET=your-oss-access-key-secret
|
|
|
|
|
|
OSS_BUCKET=jiachenlong-oss
|
|
|
|
|
|
OSS_ENDPOINT=oss-cn-hangzhou.aliyuncs.com
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 阿里云短信服务
|
|
|
|
|
|
```env
|
|
|
|
|
|
SMS_ACCESS_KEY_ID=your-sms-access-key-id
|
|
|
|
|
|
SMS_ACCESS_KEY_SECRET=your-sms-access-key-secret
|
|
|
|
|
|
SMS_SIGN_NAME=您的签名
|
|
|
|
|
|
SMS_TEMPLATE_CODE=SMS_xxx
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 请求限流配置
|
|
|
|
|
|
```env
|
|
|
|
|
|
RATE_LIMIT_ENABLED=true
|
|
|
|
|
|
RATE_LIMIT_SMS_PER_MINUTE=3
|
|
|
|
|
|
RATE_LIMIT_OCR_PER_MINUTE=10
|
|
|
|
|
|
RATE_LIMIT_BATCH_PER_MINUTE=5
|
|
|
|
|
|
RATE_LIMIT_API_PER_MINUTE=60
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 管理员账号
|
|
|
|
|
|
```env
|
|
|
|
|
|
ADMIN_USERNAME=admin
|
|
|
|
|
|
ADMIN_PASSWORD=admin123
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
---
|
|
|
|
|
|
|
2026-04-12 09:49:18 +08:00
|
|
|
|
## 部署流程
|
|
|
|
|
|
|
|
|
|
|
|
### 1. 获取代码
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
# 克隆仓库
|
|
|
|
|
|
git clone http://caibotd:Caibotd123@101.37.160.219/root/jiachenlong.git
|
|
|
|
|
|
|
|
|
|
|
|
# 切换到目标版本
|
|
|
|
|
|
cd jiachenlong
|
2026-04-12 14:24:48 +08:00
|
|
|
|
git checkout v1.2.88 # 或指定版本tag
|
2026-04-12 09:49:18 +08:00
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 2. 构建前端
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
cd frontend
|
|
|
|
|
|
npm install
|
|
|
|
|
|
npm run build
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 3. 配置后端环境变量
|
|
|
|
|
|
|
|
|
|
|
|
在后端服务器创建 `.env` 文件:
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
cat > /root/jiachenlong/backend/.env << 'EOF'
|
|
|
|
|
|
# 主数据库 - jiachenlong
|
2026-04-12 14:24:48 +08:00
|
|
|
|
DATABASE_URL=postgresql://jiachenlong:Passwd1%403@pgm-bp1t5w248t7s1pvr.pg.rds.aliyuncs.com:5432/jiachenlong
|
2026-04-12 09:49:18 +08:00
|
|
|
|
|
|
|
|
|
|
# 一尘数据库 - coolbot_data
|
2026-04-12 14:24:48 +08:00
|
|
|
|
COOLBOT_DB_URL=postgresql://coolbot:Coolbot123@pgm-bp1t1008h019ez6c.pg.rds.aliyuncs.com:5432/coolbot_data
|
2026-04-12 09:49:18 +08:00
|
|
|
|
|
2026-04-12 14:24:48 +08:00
|
|
|
|
# JWT
|
2026-04-12 09:49:18 +08:00
|
|
|
|
SECRET_KEY=jiachenlong-production-secret-key-2026
|
2026-04-12 14:24:48 +08:00
|
|
|
|
ALGORITHM=HS256
|
|
|
|
|
|
ACCESS_TOKEN_EXPIRE_MINUTES=10080
|
|
|
|
|
|
|
|
|
|
|
|
# 阿里云百炼AI
|
|
|
|
|
|
DASHSCOPE_API_KEY=your-dashscope-api-key
|
|
|
|
|
|
|
|
|
|
|
|
# 阿里云OSS
|
|
|
|
|
|
OSS_ACCESS_KEY_ID=your-oss-access-key-id
|
|
|
|
|
|
OSS_ACCESS_KEY_SECRET=your-oss-access-key-secret
|
|
|
|
|
|
OSS_BUCKET=jiachenlong-oss
|
|
|
|
|
|
OSS_ENDPOINT=oss-cn-hangzhou.aliyuncs.com
|
|
|
|
|
|
|
|
|
|
|
|
# 阿里云SMS
|
|
|
|
|
|
SMS_ACCESS_KEY_ID=your-sms-access-key-id
|
|
|
|
|
|
SMS_ACCESS_KEY_SECRET=your-sms-access-key-secret
|
|
|
|
|
|
SMS_SIGN_NAME=您的签名
|
|
|
|
|
|
SMS_TEMPLATE_CODE=SMS_xxx
|
|
|
|
|
|
|
|
|
|
|
|
# 限流
|
|
|
|
|
|
RATE_LIMIT_ENABLED=true
|
|
|
|
|
|
RATE_LIMIT_SMS_PER_MINUTE=3
|
|
|
|
|
|
RATE_LIMIT_OCR_PER_MINUTE=10
|
|
|
|
|
|
RATE_LIMIT_BATCH_PER_MINUTE=5
|
|
|
|
|
|
RATE_LIMIT_API_PER_MINUTE=60
|
|
|
|
|
|
|
|
|
|
|
|
# 管理员
|
|
|
|
|
|
ADMIN_USERNAME=admin
|
|
|
|
|
|
ADMIN_PASSWORD=admin123
|
2026-04-12 09:49:18 +08:00
|
|
|
|
EOF
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 4. 上传文件到服务器
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
# 上传前端
|
|
|
|
|
|
scp -r frontend/dist/* root@47.111.184.210:/var/www/html/
|
|
|
|
|
|
|
|
|
|
|
|
# 上传后端
|
|
|
|
|
|
scp -r backend/app root@47.111.184.210:/root/jiachenlong/backend/
|
2026-04-12 14:24:48 +08:00
|
|
|
|
scp backend/requirements.txt root@47.111.184.210:/root/jiachenlong/backend/
|
|
|
|
|
|
scp backend/.env root@47.111.184.210:/root/jiachenlong/backend/
|
2026-04-12 09:49:18 +08:00
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 5. 配置Nginx
|
|
|
|
|
|
|
|
|
|
|
|
D测试环境配置示例 (`/etc/nginx/nginx.conf`):
|
|
|
|
|
|
|
|
|
|
|
|
```nginx
|
|
|
|
|
|
user nginx;
|
|
|
|
|
|
worker_processes auto;
|
|
|
|
|
|
error_log /var/log/nginx/error.log;
|
|
|
|
|
|
pid /run/nginx.pid;
|
|
|
|
|
|
|
|
|
|
|
|
events {
|
|
|
|
|
|
worker_connections 1024;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
http {
|
2026-04-12 14:24:48 +08:00
|
|
|
|
include /etc/nginx/mime.types;
|
|
|
|
|
|
default_type application/octet-stream;
|
|
|
|
|
|
|
|
|
|
|
|
# 日志格式
|
|
|
|
|
|
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
|
|
|
|
|
|
'$status $body_bytes_sent "$http_referer" '
|
|
|
|
|
|
'"$http_user_agent" "$http_x_forwarded_for"';
|
|
|
|
|
|
|
|
|
|
|
|
access_log /var/log/nginx/access.log main;
|
|
|
|
|
|
|
|
|
|
|
|
sendfile on;
|
|
|
|
|
|
tcp_nopush on;
|
|
|
|
|
|
tcp_nodelay on;
|
|
|
|
|
|
keepalive_timeout 65;
|
|
|
|
|
|
types_hash_max_size 2048;
|
|
|
|
|
|
|
|
|
|
|
|
# Gzip压缩
|
|
|
|
|
|
gzip on;
|
|
|
|
|
|
gzip_vary on;
|
|
|
|
|
|
gzip_min_length 1024;
|
|
|
|
|
|
gzip_types text/plain text/css text/xml text/javascript application/javascript application/json application/xml;
|
2026-04-12 09:49:18 +08:00
|
|
|
|
|
|
|
|
|
|
server {
|
|
|
|
|
|
listen 80;
|
|
|
|
|
|
server_name _;
|
2026-04-12 14:24:48 +08:00
|
|
|
|
|
|
|
|
|
|
# 前端静态文件
|
2026-04-12 09:49:18 +08:00
|
|
|
|
root /var/www/html;
|
|
|
|
|
|
index index.html;
|
2026-04-12 14:24:48 +08:00
|
|
|
|
|
|
|
|
|
|
# 大文件上传限制
|
|
|
|
|
|
client_max_body_size 50M;
|
|
|
|
|
|
client_body_timeout 300s;
|
|
|
|
|
|
|
|
|
|
|
|
# 前端静态资源缓存
|
|
|
|
|
|
location ~* \.(js|css|png|jpg|jpeg|gif|ico|svg|woff|woff2|ttf|eot)$ {
|
|
|
|
|
|
expires 30d;
|
|
|
|
|
|
add_header Cache-Control "public, immutable";
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
# 前端 SPA 路由
|
2026-04-12 09:49:18 +08:00
|
|
|
|
location / {
|
|
|
|
|
|
try_files $uri $uri/ /index.html;
|
|
|
|
|
|
}
|
2026-04-12 14:24:48 +08:00
|
|
|
|
|
2026-04-12 09:49:18 +08:00
|
|
|
|
# API代理到后端
|
|
|
|
|
|
location /api/ {
|
|
|
|
|
|
proxy_pass http://127.0.0.1:3000;
|
2026-04-12 14:24:48 +08:00
|
|
|
|
proxy_http_version 1.1;
|
2026-04-12 09:49:18 +08:00
|
|
|
|
proxy_set_header Host $host;
|
|
|
|
|
|
proxy_set_header X-Real-IP $remote_addr;
|
2026-04-12 14:24:48 +08:00
|
|
|
|
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
|
|
|
|
|
proxy_set_header X-Forwarded-Proto $scheme;
|
|
|
|
|
|
proxy_read_timeout 300s;
|
|
|
|
|
|
proxy_connect_timeout 75s;
|
2026-04-12 09:49:18 +08:00
|
|
|
|
}
|
2026-04-12 14:24:48 +08:00
|
|
|
|
|
2026-04-12 09:49:18 +08:00
|
|
|
|
# 上传文件代理
|
|
|
|
|
|
location /uploads/ {
|
|
|
|
|
|
proxy_pass http://127.0.0.1:3000;
|
2026-04-12 14:24:48 +08:00
|
|
|
|
proxy_set_header Host $host;
|
|
|
|
|
|
proxy_set_header X-Real-IP $remote_addr;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
# 静态文件服务
|
|
|
|
|
|
location /static/ {
|
|
|
|
|
|
alias /var/www/html/static/;
|
|
|
|
|
|
expires 30d;
|
2026-04-12 09:49:18 +08:00
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 6. 启动后端服务
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
# 激活conda环境
|
|
|
|
|
|
source /opt/conda/etc/profile.d/conda.sh
|
|
|
|
|
|
conda activate py312
|
|
|
|
|
|
|
2026-04-12 14:24:48 +08:00
|
|
|
|
# 安装依赖(如需要)
|
|
|
|
|
|
pip install -r requirements.txt
|
|
|
|
|
|
|
|
|
|
|
|
# 创建日志目录
|
|
|
|
|
|
mkdir -p /root/jiachenlong/backend/logs
|
|
|
|
|
|
|
2026-04-12 09:49:18 +08:00
|
|
|
|
# 设置Python路径
|
|
|
|
|
|
export PYTHONPATH=/root/jiachenlong/backend
|
|
|
|
|
|
|
|
|
|
|
|
# 启动后端
|
|
|
|
|
|
cd /root/jiachenlong/backend
|
|
|
|
|
|
nohup python -m uvicorn app.main:app --host 0.0.0.0 --port 3000 > logs/api.log 2>&1 &
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 7. 重启Nginx
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
# 测试配置
|
|
|
|
|
|
nginx -t
|
|
|
|
|
|
|
|
|
|
|
|
# 重载配置
|
|
|
|
|
|
nginx -s reload
|
|
|
|
|
|
|
|
|
|
|
|
# 或完全重启
|
2026-04-12 14:24:48 +08:00
|
|
|
|
killall nginx && nginx
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
---
|
|
|
|
|
|
|
|
|
|
|
|
## SSL证书配置 (Let's Encrypt)
|
|
|
|
|
|
|
|
|
|
|
|
### 安装 Certbot
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
# CentOS/RHEL
|
|
|
|
|
|
yum install epel-release
|
|
|
|
|
|
yum install certbot python3-certbot-nginx
|
|
|
|
|
|
|
|
|
|
|
|
# 或使用 pip
|
|
|
|
|
|
pip install certbot certbot-nginx
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 获取证书
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
# 停止 Nginx(如果正在运行)
|
|
|
|
|
|
nginx -s stop
|
|
|
|
|
|
|
|
|
|
|
|
# 获取证书(单域名)
|
|
|
|
|
|
certbot certonly --standalone -d jiachenlong.com --agree-tos --email admin@jiachenlong.com --no-eff-email
|
|
|
|
|
|
|
|
|
|
|
|
# 获取证书(多域名)
|
|
|
|
|
|
certbot certonly --standalone -d jiachenlong.com -d www.jiachenlong.com --agree-tos --email admin@jiachenlong.com --no-eff-email
|
|
|
|
|
|
|
|
|
|
|
|
# 重启 Nginx
|
2026-04-12 09:49:18 +08:00
|
|
|
|
nginx
|
|
|
|
|
|
```
|
|
|
|
|
|
|
2026-04-12 14:24:48 +08:00
|
|
|
|
### 自动续期
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
# 测试续期(dry-run)
|
|
|
|
|
|
certbot renew --dry-run
|
|
|
|
|
|
|
|
|
|
|
|
# 设置定时任务(每天凌晨自动续期)
|
|
|
|
|
|
crontab -e
|
|
|
|
|
|
# 添加以下行:
|
|
|
|
|
|
# 0 3 * * * certbot renew --quiet --deploy-hook "nginx -s reload"
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### Nginx HTTPS 配置
|
|
|
|
|
|
|
|
|
|
|
|
```nginx
|
|
|
|
|
|
server {
|
|
|
|
|
|
listen 80;
|
|
|
|
|
|
server_name jiachenlong.com www.jiachenlong.com;
|
|
|
|
|
|
return 301 https://$server_name$request_uri;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
server {
|
|
|
|
|
|
listen 443 ssl http2;
|
|
|
|
|
|
server_name jiachenlong.com www.jiachenlong.com;
|
|
|
|
|
|
|
|
|
|
|
|
# SSL证书
|
|
|
|
|
|
ssl_certificate /etc/letsencrypt/live/jiachenlong.com/fullchain.pem;
|
|
|
|
|
|
ssl_certificate_key /etc/letsencrypt/live/jiachenlong.com/privkey.pem;
|
|
|
|
|
|
|
|
|
|
|
|
# SSL安全配置
|
|
|
|
|
|
ssl_session_timeout 1d;
|
|
|
|
|
|
ssl_session_cache shared:SSL:50m;
|
|
|
|
|
|
ssl_session_tickets off;
|
|
|
|
|
|
|
|
|
|
|
|
ssl_protocols TLSv1.2 TLSv1.3;
|
|
|
|
|
|
ssl_ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384;
|
|
|
|
|
|
ssl_prefer_server_ciphers off;
|
|
|
|
|
|
|
|
|
|
|
|
add_header Strict-Transport-Security "max-age=63072000" always;
|
|
|
|
|
|
|
|
|
|
|
|
# ... 其余配置同上 ...
|
|
|
|
|
|
}
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
---
|
|
|
|
|
|
|
|
|
|
|
|
## 数据库迁移 (Alembic)
|
|
|
|
|
|
|
|
|
|
|
|
### 查看当前版本
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
cd /root/jiachenlong/backend
|
|
|
|
|
|
source /opt/conda/etc/profile.d/conda.sh && conda activate py312
|
|
|
|
|
|
export PYTHONPATH=/root/jiachenlong/backend
|
|
|
|
|
|
|
|
|
|
|
|
alembic current
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 查看迁移历史
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
alembic history --verbose
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 创建新迁移
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
# 自动生成迁移脚本(根据模型变更)
|
|
|
|
|
|
alembic revision --autogenerate -m "描述变更内容"
|
|
|
|
|
|
|
|
|
|
|
|
# 手动创建空白迁移
|
|
|
|
|
|
alembic revision -m "描述变更内容"
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 执行迁移
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
# 升级到最新版本
|
|
|
|
|
|
alembic upgrade head
|
|
|
|
|
|
|
|
|
|
|
|
# 升级到指定版本
|
|
|
|
|
|
alembic upgrade <revision_id>
|
|
|
|
|
|
|
|
|
|
|
|
# 检查是否有待执行迁移
|
|
|
|
|
|
alembic check
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 回滚
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
# 回滚一步
|
|
|
|
|
|
alembic downgrade -1
|
|
|
|
|
|
|
|
|
|
|
|
# 回滚到初始状态
|
|
|
|
|
|
alembic downgrade base
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 生产环境迁移流程
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
# 1. 在测试环境验证迁移
|
|
|
|
|
|
alembic upgrade head
|
|
|
|
|
|
|
|
|
|
|
|
# 2. 检查数据完整性
|
|
|
|
|
|
# (在测试环境执行应用相关测试)
|
|
|
|
|
|
|
|
|
|
|
|
# 3. 在生产环境执行迁移(建议在低峰期)
|
|
|
|
|
|
alembic upgrade head
|
|
|
|
|
|
|
|
|
|
|
|
# 4. 重启后端服务
|
|
|
|
|
|
pkill -f 'uvicorn app.main:app'
|
|
|
|
|
|
nohup python -m uvicorn app.main:app --host 0.0.0.0 --port 3000 > logs/api.log 2>&1 &
|
|
|
|
|
|
```
|
|
|
|
|
|
|
2026-04-12 09:49:18 +08:00
|
|
|
|
---
|
|
|
|
|
|
|
|
|
|
|
|
## 常见问题与解决方案
|
|
|
|
|
|
|
|
|
|
|
|
### 1. 后端启动失败:`address already in use`
|
|
|
|
|
|
|
|
|
|
|
|
**原因**:端口被占用
|
|
|
|
|
|
|
|
|
|
|
|
**解决**:
|
|
|
|
|
|
```bash
|
|
|
|
|
|
# 查看占用进程
|
|
|
|
|
|
fuser 3000/tcp
|
|
|
|
|
|
|
|
|
|
|
|
# 杀死占用进程
|
|
|
|
|
|
fuser -k 3000/tcp
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 2. 后端启动失败:`ModuleNotFoundError: No module named 'xxx'`
|
|
|
|
|
|
|
|
|
|
|
|
**原因**:Python依赖缺失
|
|
|
|
|
|
|
|
|
|
|
|
**解决**:
|
|
|
|
|
|
```bash
|
|
|
|
|
|
pip install -r requirements.txt
|
|
|
|
|
|
# 或安装特定依赖
|
|
|
|
|
|
pip install bcrypt passlib python-jose python-multipart email-validator oss2 Pillow
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 3. API返回500错误:`name 'response' is not defined`
|
|
|
|
|
|
|
|
|
|
|
|
**原因**:FastAPI函数参数中使用了`response: Response = None`,但该参数已被废弃或删除
|
|
|
|
|
|
|
|
|
|
|
|
**解决**:检查并修复 `app/routers/*.py` 文件中的 `response.headers` 使用
|
|
|
|
|
|
|
|
|
|
|
|
```python
|
|
|
|
|
|
# 找到类似代码
|
|
|
|
|
|
response.headers['X-Total-Pages'] = str(total_pages)
|
|
|
|
|
|
|
|
|
|
|
|
# 删除这些行(它们不是必需的)
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 4. 数据库连接失败:`could not translate host name`
|
|
|
|
|
|
|
|
|
|
|
|
**原因**:主机名未正确解析
|
|
|
|
|
|
|
|
|
|
|
|
**解决**:确保 `.env` 中的数据库地址使用完整域名
|
|
|
|
|
|
```bash
|
|
|
|
|
|
# 错误
|
|
|
|
|
|
DB_HOST=pgm-bp1t5w248t7s1pvr
|
|
|
|
|
|
|
|
|
|
|
|
# 正确
|
|
|
|
|
|
DB_HOST=pgm-bp1t5w248t7s1pvr.pg.rds.aliyuncs.com
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 5. 数据库连接失败:密码中特殊字符问题
|
|
|
|
|
|
|
|
|
|
|
|
**原因**:密码中的 `@` 符号导致URL解析错误
|
|
|
|
|
|
|
|
|
|
|
|
**解决**:URL编码密码
|
|
|
|
|
|
```bash
|
|
|
|
|
|
# 密码 Passwd1@3 编码为 Passwd1%403
|
|
|
|
|
|
DATABASE_URL=postgresql://jiachenlong:Passwd1%403@...
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 6. 前端403 Forbidden
|
|
|
|
|
|
|
|
|
|
|
|
**原因**:文件权限问题
|
|
|
|
|
|
|
|
|
|
|
|
**解决**:
|
|
|
|
|
|
```bash
|
|
|
|
|
|
chown -R nginx:nginx /var/www/html
|
|
|
|
|
|
chmod -R 755 /var/www/html
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 7. Nginx配置错误:`server directive is not allowed here`
|
|
|
|
|
|
|
|
|
|
|
|
**原因**:nginx配置文件放在HTTP块外面
|
|
|
|
|
|
|
|
|
|
|
|
**解决**:确保server块在http块内部
|
|
|
|
|
|
|
|
|
|
|
|
### 8. 前端显示旧版本
|
|
|
|
|
|
|
|
|
|
|
|
**原因**:浏览器缓存
|
|
|
|
|
|
|
|
|
|
|
|
**解决**:强制刷新 (Ctrl+Shift+R) 或清除缓存
|
|
|
|
|
|
|
2026-04-12 14:24:48 +08:00
|
|
|
|
### 9. 后端日志显示数据库连接超时
|
|
|
|
|
|
|
|
|
|
|
|
**原因**:数据库地址不可达或网络问题
|
|
|
|
|
|
|
|
|
|
|
|
**解决**:
|
|
|
|
|
|
```bash
|
|
|
|
|
|
# 测试连接
|
|
|
|
|
|
telnet pgm-bp1t5w248t7s1pvr.pg.rds.aliyuncs.com 5432
|
|
|
|
|
|
|
|
|
|
|
|
# 或
|
|
|
|
|
|
nc -zv pgm-bp1t5w248t7s1pvr.pg.rds.aliyuncs.com 5432
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### 10. 文件上传失败 413 Request Entity Too Large
|
|
|
|
|
|
|
|
|
|
|
|
**原因**:Nginx `client_max_body_size` 限制
|
|
|
|
|
|
|
|
|
|
|
|
**解决**:在 nginx.conf 的 http 或 server 块中添加:
|
|
|
|
|
|
```nginx
|
|
|
|
|
|
client_max_body_size 50M;
|
|
|
|
|
|
```
|
|
|
|
|
|
|
2026-04-12 09:49:18 +08:00
|
|
|
|
---
|
|
|
|
|
|
|
|
|
|
|
|
## 代码修改注意事项
|
|
|
|
|
|
|
2026-04-12 14:24:48 +08:00
|
|
|
|
### information.py / collections.py 常见问题
|
2026-04-12 09:49:18 +08:00
|
|
|
|
|
|
|
|
|
|
1. **Response参数问题**
|
|
|
|
|
|
- 函数签名中的 `response: Response = None` 会导致 `NameError`
|
|
|
|
|
|
- 如果不需要修改响应头,应该直接删除这个参数
|
|
|
|
|
|
- 同时删除函数体内使用 `response.headers` 的代码
|
|
|
|
|
|
|
|
|
|
|
|
2. **处理方法**:
|
|
|
|
|
|
```python
|
|
|
|
|
|
# 错误写法
|
|
|
|
|
|
def get_list(response: Response = None):
|
|
|
|
|
|
response.headers['X-Total'] = '100' # 会报错
|
|
|
|
|
|
|
|
|
|
|
|
# 正确写法
|
|
|
|
|
|
def get_list():
|
|
|
|
|
|
# 不使用response.headers,或使用Response参数的正确方式
|
|
|
|
|
|
pass
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
### collections.py 统计接口
|
|
|
|
|
|
|
|
|
|
|
|
- `get_current_user` 可能返回 `None`
|
|
|
|
|
|
- 访问 `current_user.role` 前必须检查 `current_user` 是否为 `None`
|
|
|
|
|
|
|
|
|
|
|
|
```python
|
|
|
|
|
|
# 错误
|
|
|
|
|
|
if current_user.role == "admin":
|
|
|
|
|
|
|
|
|
|
|
|
# 正确
|
|
|
|
|
|
if not current_user or current_user.role != "admin":
|
|
|
|
|
|
return {"totalCount": 0}
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
---
|
|
|
|
|
|
|
2026-04-12 14:24:48 +08:00
|
|
|
|
## 改进建议(已完成)
|
2026-04-12 09:49:18 +08:00
|
|
|
|
|
2026-04-12 14:24:48 +08:00
|
|
|
|
- [x] 使用 `python-dotenv` 管理环境变量 → `backend/.env.example`
|
|
|
|
|
|
- [x] Alembic 数据库迁移管理 → `backend/alembic/`
|
|
|
|
|
|
- [x] 单元测试框架 → `backend/tests/`
|
|
|
|
|
|
- [ ] 自动化部署脚本 (deploy.sh)
|
2026-04-12 09:49:18 +08:00
|
|
|
|
- [ ] CI/CD 自动化测试
|
2026-04-12 14:24:48 +08:00
|
|
|
|
- [ ] 健康检查端点
|
2026-04-12 09:49:18 +08:00
|
|
|
|
|
|
|
|
|
|
---
|
|
|
|
|
|
|
|
|
|
|
|
## 快速命令参考
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
2026-04-12 14:24:48 +08:00
|
|
|
|
# ========== 后端管理 ==========
|
2026-04-12 09:49:18 +08:00
|
|
|
|
# 查看后端进程
|
|
|
|
|
|
ps aux | grep uvicorn | grep -v grep
|
|
|
|
|
|
|
|
|
|
|
|
# 查看后端日志
|
|
|
|
|
|
tail -f /root/jiachenlong/backend/logs/api.log
|
|
|
|
|
|
|
|
|
|
|
|
# 重启后端
|
|
|
|
|
|
pkill -f 'uvicorn app.main:app'
|
|
|
|
|
|
cd /root/jiachenlong/backend
|
|
|
|
|
|
source /opt/conda/etc/profile.d/conda.sh && conda activate py312
|
|
|
|
|
|
export PYTHONPATH=/root/jiachenlong/backend
|
|
|
|
|
|
nohup python -m uvicorn app.main:app --host 0.0.0.0 --port 3000 > logs/api.log 2>&1 &
|
|
|
|
|
|
|
2026-04-12 14:24:48 +08:00
|
|
|
|
# ========== 测试API ==========
|
2026-04-12 09:49:18 +08:00
|
|
|
|
curl http://localhost:3000/api/collections/stats
|
|
|
|
|
|
curl http://localhost:3000/api/information/list?info_type=seek
|
|
|
|
|
|
|
2026-04-12 14:24:48 +08:00
|
|
|
|
# ========== Nginx ==========
|
2026-04-12 09:49:18 +08:00
|
|
|
|
nginx -t # 测试配置
|
|
|
|
|
|
nginx -s reload # 重载配置
|
|
|
|
|
|
nginx -s stop # 停止
|
|
|
|
|
|
killall nginx && nginx # 完全重启
|
2026-04-12 14:24:48 +08:00
|
|
|
|
|
|
|
|
|
|
# ========== 数据库迁移 ==========
|
|
|
|
|
|
cd /root/jiachenlong/backend
|
|
|
|
|
|
export PYTHONPATH=/root/jiachenlong/backend
|
|
|
|
|
|
alembic current # 查看当前版本
|
|
|
|
|
|
alembic history # 查看历史
|
|
|
|
|
|
alembic upgrade head # 执行迁移
|
|
|
|
|
|
alembic downgrade -1 # 回滚一步
|
|
|
|
|
|
|
|
|
|
|
|
# ========== SSL证书 ==========
|
|
|
|
|
|
certbot renew --dry-run # 测试续期
|
|
|
|
|
|
certbot renew --quiet # 执行续期
|
2026-04-12 09:49:18 +08:00
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
---
|
|
|
|
|
|
|
2026-04-12 14:24:48 +08:00
|
|
|
|
*最后更新:2026-04-12*
|