适用:Ubuntu 24.04 LTS 全新安装
版本:v2.0
最后更新:2026-07-14
| 项目 | 最低 | 推荐 |
|---|---|---|
| CPU | 4 核 | 8 核 |
| 内存 | 8 GB | 16 GB |
| 系统盘 | 50 GB SSD | 100 GB SSD |
| 操作系统 | Ubuntu 22.04+ | Ubuntu 24.04 LTS |
| 网络 | 公网 IP | 公网 IP + 域名 |
不需要 GPU(LLM 走阿里云 Qwen API)。
① 基础环境 → apt update, 装 git/curl 等
② Docker → 容器运行时
③ 拉取代码 → git clone 到 /opt/pharmacopoeia-ai
④ 环境变量 → .env 配置
⑤ PostgreSQL → Docker 启动 pgvector
⑥ 数据库建表 → 导入 schema.sql
⑦ Python 后端 → venv + FastAPI + Supervisor 守护
⑧ Nginx → 反向代理 + SSE 免缓冲
⑨ 防火墙 → ufw 只开放 80/443
⑩ 备份 + 日志 → cron 每日备份
# 更新系统
sudo apt update && sudo apt upgrade -y
# 安装基础工具
sudo apt install -y curl wget git vim htop ca-certificates gnupg lsb-release
# 设置时区
sudo timedatectl set-timezone Asia/Shanghai
# 官方安装脚本
curl -fsSL https://get.docker.com | sudo bash
# 把当前用户加入 docker 组(不用每次 sudo)
sudo usermod -aG docker $USER
newgrp docker
# 验证
docker --version
docker compose version
Docker 镜像拉取慢的话,配置国内镜像加速:
> sudo tee /etc/docker/daemon.json << 'EOF' > { > "registry-mirrors": ["https://docker.m.daocloud.io"] > } > EOF > sudo systemctl restart docker > ``` --- ### ③ 拉取项目代码bash
创建应用目录
sudo mkdir -p /opt/pharmacopoeia-ai sudo chown $USER:$USER /opt/pharmacopoeia-ai
cd /opt/pharmacopoeia-ai git clone https://github.com/your-org/pharmacopoeia-ai.git .
ls -la
---
### ④ 配置环境变量
bash cd /opt/pharmacopoeia-ai
cp .env.example .env
echo "SECRET_KEY=$(openssl rand -hex 32)" echo "DB_PASSWORD=$(openssl rand -base64 16)"
编辑 `.env`,修改以下值:
bash vim .env
ini
APP_ENV=production APP_DEBUG=false SECRET_KEY=<上面生成的随机密钥>
POSTGRES_PASSWORD=<上面生成的数据库密码>
QWEN_API_KEY=sk-xxxxxxxxxxxxxxxx # 阿里云百炼 API Key
WECHAT_APPID=wx1234567890 WECHAT_SECRET=xxxxxxxx
QWEN_MAX_TOKENS=2048 LOG_LEVEL=WARNING
> **Qwen API Key 获取**:注册 [阿里云百炼](https://bailian.console.aliyun.com/) → 模型广场 → 选择 qwen-max → API-KEY 管理 → 创建 API Key。
>
> 新用户有免费额度,足够开发测试。
---
### ⑤ 启动 PostgreSQL + Redis
bash cd /opt/pharmacopoeia-ai/deploy
source /opt/pharmacopoeia-ai/.env
docker compose up -d
sleep 10 docker ps
docker exec pharmacopoeia-pg psql -U postgres -d pharmacopoeia -c "SELECT 1"
docker exec pharmacopoeia-redis redis-cli ping
docker update --restart=always pharmacopoeia-pg pharmacopoeia-redis
---
### ⑥ 初始化数据库表
bash
docker exec -i pharmacopoeia-pg psql -U postgres -d pharmacopoeia \ < /opt/pharmacopoeia-ai/database/schema.sql
docker exec pharmacopoeia-pg psql -U postgres -d pharmacopoeia -c "\dt"
9 张表说明:
| 表 | 用途 |
|---|------|
| `drugs` | 药品主表 |
| `drug_chunks` | 药品切片 + 1024维向量(RAG 核心) |
| `knowledge_points` | 执业药师知识点 |
| `questions` | 题库 |
| `conversations` | 对话会话 |
| `messages` | 对话消息 |
| `users` | 用户 |
| `user_progress` | 学习进度 |
| `answer_records` | 答题记录 |
---
### ⑦ 编译并启动 Java 后端
#### 7.1 编译
bash cd /opt/pharmacopoeia-ai/backend-java
mvn clean package -DskipTests
#### 7.2 手动启动测试
bash
export POSTGRES_PASSWORD=postgres
java -jar target/pharmacopoeia-ai-1.0.0.jar
#### 7.3 使用启动脚本管理
bash
chmod +x /opt/pharmacopoeia-ai/tools/start-java.sh
bash /opt/pharmacopoeia-ai/tools/start-java.sh start
bash /opt/pharmacopoeia-ai/tools/start-java.sh status
bash /opt/pharmacopoeia-ai/tools/start-java.sh logs
bash /opt/pharmacopoeia-ai/tools/start-java.sh restart
bash /opt/pharmacopoeia-ai/tools/start-java.sh stop
#### 7.4 配置 Supervisor 守护进程(推荐)
bash sudo apt install -y supervisor
sudo mkdir -p /var/log/pharmacopoeia
sudo cp /opt/pharmacopoeia-ai/deploy/supervisord-java.conf /etc/supervisor/conf.d/pharmacopoeia.conf
sudo vim /etc/supervisor/conf.d/pharmacopoeia.conf
sudo supervisorctl reread sudo supervisorctl update sudo supervisorctl start pharmacopoeia-backend
sudo supervisorctl status
---
### ⑧ 配置 Nginx
bash
sudo apt install -y nginx
sudo tee /etc/nginx/sites-available/pharmacopoeia << 'NGINX'
upstream backend {
server 127.0.0.1:8000;
keepalive 64;
}
limit_req_zone $binary_remote_addr zone=api_limit:10m rate=60r/m;
server {
listen 80;
server_name _;
client_max_body_size 10m;
# Gzip
gzip on;
gzip_vary on;
gzip_min_length 1024;
gzip_types text/plain text/css application/json application/javascript text/xml application/xml text/javascript;
# 安全头
add_header X-Frame-Options "SAMEORIGIN" always;
add_header X-Content-Type-Options "nosniff" always;
add_header X-XSS-Protection "1; mode=block" always;
# API 反向代理(SSE 流式关键:禁用缓冲)
location /api/ {
proxy_pass http://backend;
proxy_http_version 1.1;
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_set_header Connection "";
# SSE 支持
proxy_buffering off;
proxy_cache off;
proxy_read_timeout 300s;
# 限流
limit_req zone=api_limit burst=20 nodelay;
}
# 健康检查(不记录日志)
location /health {
proxy_pass http://backend;
access_log off;
}
# API 文档
location /docs {
proxy_pass http://backend;
}
# 静态文件
location /static/ {
alias /opt/pharmacopoeia-ai/static/;
expires 7d;
add_header Cache-Control "public, immutable";
}
# 根路径 → 前端页面
location / {
alias /opt/pharmacopoeia-ai/static/;
try_files $uri /index.html;
}
} NGINX
sudo ln -sf /etc/nginx/sites-available/pharmacopoeia /etc/nginx/sites-enabled/ sudo rm -f /etc/nginx/sites-enabled/default
sudo nginx -t
sudo systemctl reload nginx sudo systemctl enable nginx
**验证**:浏览器访问 `http://服务器IP/` 应该看到前端页面。
---
### ⑨ 配置防火墙
bash
sudo apt install -y ufw
sudo ufw allow 22/tcp # SSH sudo ufw allow 80/tcp # HTTP sudo ufw allow 443/tcp # HTTPS
sudo ufw --force enable sudo ufw status verbose
> PostgreSQL (5432)、Redis (6379)、FastAPI (8000) **不对外开放**,只通过本地回环访问。
---
### ⑩ 数据库备份
bash
sudo tee /opt/pharmacopoeia-ai/tools/backup.sh << 'EOF' #!/bin/bash BACKUP_DIR="/opt/backups/pharmacopoeia" mkdir -p "$BACKUPDIR" DATE=$(date +%Y%m%d%H%M%S) docker exec pharmacopoeia-pg pg_dump -U postgres pharmacopoeia
"$BACKUPDIR/pg${DATE}.sql"
保留最近 7 天
find "$BACKUPDIR" -name "pg*.sql" -mtime +7 -delete echo "$(date '+%F %T') backup done: pg_${DATE}.sql" >> /var/log/pharmacopoeia/backup.log EOF sudo chmod +x /opt/pharmacopoeia-ai/tools/backup.sh
(crontab -l 2>/dev/null; echo "0 2 * * * /opt/pharmacopoeia-ai/tools/backup.sh") | crontab -
---
## 四、配置域名和 SSL(有域名后执行)
bash
sudo apt install -y certbot python3-certbot-nginx
sudo vim /etc/nginx/sites-available/pharmacopoeia
sudo nginx -t && sudo systemctl reload nginx
sudo certbot --nginx -d yaodian.example.com
sudo certbot renew --dry-run
---
## 五、导入数据(有药品数据后执行)
bash cd /opt/pharmacopoeia-ai/data-pipeline
python3 -m venv venv source venv/bin/activate pip install -r requirements.txt
python ingest.py
---
## 六、最终验证清单
部署完成后逐项确认:
bash
docker ps | grep pharmacopoeia
docker exec pharmacopoeia-pg psql -U postgres -d pharmacopoeia -c "SELECT count(*) FROM information_schema.tables WHERE table_schema='public'"
sudo supervisorctl status pharmacopoeia-backend
curl http://localhost:8000/health
sudo ufw status | grep -E "80|443"
---
## 七、日常运维命令
| 操作 | 命令 |
|------|------|
| 查看后端状态 | `sudo supervisorctl status` |
| 重启后端 | `sudo supervisorctl restart pharmacopoeia-backend` |
| 查看后端实时日志 | `sudo supervisorctl tail -f pharmacopoeia-backend` |
| 查看错误日志 | `tail -100 /var/log/pharmacopoeia/backend-error.log` |
| 重启 Nginx | `sudo systemctl reload nginx` |
| 重启 PG | `docker restart pharmacopoeia-pg` |
| 重启 Redis | `docker restart pharmacopoeia-redis` |
| 进入 PG 控制台 | `docker exec -it pharmacopoeia-pg psql -U postgres -d pharmacopoeia` |
| 手动备份 | `bash /opt/pharmacopoeia-ai/tools/backup.sh` |
| 更新代码并重启 | `cd /opt/pharmacopoeia-ai && git pull && sudo supervisorctl restart pharmacopoeia-backend` |
| 查看磁盘 | `df -h` |
| 查看内存 | `free -h` |
---
## 八、部署架构图
公网用户
│
▼
┌──────────────────┐ │ UFW 防火墙 │ 开放: 22, 80, 443 └────────┬─────────┘
│
▼
┌──────────────────┐ │ Nginx :80/:443 │ SSL / 反向代理 / 限流 / 静态文件 └────────┬─────────┘
│ :8000 (本地)
▼
┌──────────────────┐ │ Supervisor │ 进程守护, 挂了自动重启 │ ┌──────────────┐ │ │ │ Uvicorn x4 │ │ │ │ FastAPI :8000│ │ │ └──────┬───────┘ │ └─────────┼─────────┘
│
┌──────┼──────┐ ▼ ▼ ▼ ┌──────┐ ┌────┐ ┌──────────┐ │ PG │ │Redis│ │ Qwen API │ │ :5432│ │:6379│ │ (阿里云) │ │Docker│ │Dockr│ │ 云端 │ └──────┘ └────┘ └──────────┘
快速管理: bash tools/start-java.sh {start|stop|restart|status|logs}
---
## 九、常见问题
### Q: pip install 报错,sentence-transformers 编译失败?
bash sudo apt install -y build-essential python3-dev
pip install sentence-transformers
### Q: docker compose 提示 .env 中的变量未生效?
bash
cd /opt/pharmacopoeia-ai/deploy ln -sf ../.env .env docker compose up -d
### Q: Qwen API 连不上?
bash
curl -I https://dashscope.aliyuncs.com
### Q: 如何查看 AI 对话是否正常工作?
bash
curl -X POST http://localhost:8000/api/v1/chat/ask \ -H "Content-Type: application/json" \ -d '{"query": "阿莫西林是什么药"}' ```