update:1.更新readme.txt
This commit is contained in:
@@ -6,12 +6,11 @@
|
||||

|
||||

|
||||

|
||||

|
||||

|
||||
|
||||
**一款基于 AI 的智能小说创作助手,帮助你轻松创作精彩故事**
|
||||
**基于 AI 的智能小说创作助手**
|
||||
|
||||
[特性](#-特性) • [快速开始](#-快速开始) • [部署方式](#-部署方式) • [配置说明](#%EF%B8%8F-配置说明) • [项目结构](#-项目结构)
|
||||
[特性](#-特性) • [快速开始](#-快速开始) • [配置说明](#%EF%B8%8F-配置说明) • [项目结构](#-项目结构)
|
||||
|
||||
</div>
|
||||
|
||||
@@ -19,42 +18,37 @@
|
||||
|
||||
## ✨ 特性
|
||||
|
||||
- 🤖 **多 AI 模型支持** - 支持 OpenAI、Google Gemini、Anthropic Claude 等主流 AI 模型
|
||||
- 📝 **智能向导** - 通过向导式引导快速创建小说项目,AI 自动生成大纲、角色和世界观
|
||||
- 👥 **角色管理** - 创建和管理小说角色,包括人物关系、组织架构等
|
||||
- 📖 **章节编辑** - 支持章节的创建、编辑、重新生成和润色功能
|
||||
- 🌐 **世界观设定** - 构建完整的故事世界观和背景设定
|
||||
- 🔐 **多种登录方式** - 支持 LinuxDO OAuth 登录和本地账户登录
|
||||
- 🐳 **Docker 部署** - 一键部署,开箱即用
|
||||
- 💾 **数据持久化** - 支持 PostgreSQL 和 SQLite 双数据库,多用户数据隔离
|
||||
- 🎨 **现代化 UI** - 基于 Ant Design 的美观界面,响应式设计
|
||||
|
||||
- 🤖 **多 AI 模型** - 支持 OpenAI、Gemini、Claude 等主流模型
|
||||
- 📝 **智能向导** - AI 自动生成大纲、角色和世界观
|
||||
- 👥 **角色管理** - 人物关系、组织架构可视化管理
|
||||
- 📖 **章节编辑** - 支持创建、编辑、重新生成和润色
|
||||
- 🌐 **世界观设定** - 构建完整的故事背景
|
||||
- 🔐 **多种登录** - LinuxDO OAuth 或本地账户登录
|
||||
- 💾 **PostgreSQL** - 生产级数据库,多用户数据隔离
|
||||
- 🐳 **Docker 部署** - 一键启动,开箱即用
|
||||
|
||||
## 📋 TODO List
|
||||
|
||||
以下是正在规划和开发中的功能:
|
||||
- [ ] **灵感模式** - 创作灵感和点子生成
|
||||
- [x] **自定义写作风格** - 支持自定义 AI 写作风格
|
||||
- [x] **数据导入导出** - 项目数据的导入导出
|
||||
- [ ] **Prompt 调整界面** - 可视化编辑 Prompt 模板
|
||||
- [x] **章节字数限制** - 用户可设置生成字数
|
||||
- [ ] **设定追溯与矛盾检测** - 自动检测设定冲突
|
||||
- [ ] **思维链与章节关系图谱** - 可视化章节逻辑关系
|
||||
- [x] **根据分析一键重写** - 根据分析建议重新生成
|
||||
- [x] **Linux DO 自动创建账号** - OAuth 登录自动生成账号
|
||||
|
||||
- [ ] **灵感模式** - 提供创作灵感和点子生成功能
|
||||
- [✔] **自定义写作风格** - 支持自定义AI写作风格和语言风格
|
||||
- [✔] **支持数据导入导出** - 支持项目数据的导入和导出功能
|
||||
- [ ] **添加prompt调整界面** - 提供可视化的prompt模板编辑和调整界面
|
||||
- [✔] **开放章节内容字数限制** - 支持用户在生成章节内容时设置字数 @wyf007
|
||||
- [ ] **设定追溯与矛盾检测** - 对大纲、世界观、角色档案中的设定支持悬停查看注释,显示相关章节来源和佐证原文;自动检测新章节与已有设定的矛盾(吃书),标记为"矛盾"设定并提供解决建议,当新设定解决矛盾后自动更新注释说明 @lulujiang
|
||||
- [ ] **思维链与章节关系图谱** - 为每章建立思维链,总结与上文的逻辑关系、明暗线发展;可选的章节关系满图功能,自动识别和标注伏笔埋设与揭晓、角色出场与呼应等内在联系,帮助提升小说结构的紧密性和连贯性 @lulujiang
|
||||
- [ ] **根据分析建议一键重写** - 根据分析的的建议,实现一键重新生成章节内容
|
||||
- [ ] **Linux DO登录自动创建账号** - 使用Linux DO登录后,自动生成系统账号
|
||||
|
||||
> 💡 如果你有其他功能建议,欢迎提交 Issue 或 Pull Request!
|
||||
> 💡 欢迎提交 Issue 或 Pull Request!
|
||||
|
||||
## 🚀 快速开始
|
||||
|
||||
### 前置要求
|
||||
|
||||
- **Docker 部署**:Docker 和 Docker Compose
|
||||
- **本地开发**:Python 3.11+ 和 Node.js 18+
|
||||
- **必需**:至少一个 AI 服务的 API Key(OpenAI/Gemini/Anthropic)
|
||||
- Docker 和 Docker Compose
|
||||
- 至少一个 AI 服务的 API Key(OpenAI/Gemini/Claude)
|
||||
|
||||
### 方式一:从源码构建 Docker 镜像
|
||||
### Docker Compose 部署(推荐)
|
||||
|
||||
```bash
|
||||
# 1. 克隆项目
|
||||
@@ -63,142 +57,136 @@ cd MuMuAINovel
|
||||
|
||||
# 2. 配置环境变量
|
||||
cp backend/.env.example .env
|
||||
# 编辑 .env 文件,填入你的 API Keys
|
||||
# 编辑 .env 文件,填入必要配置
|
||||
|
||||
# 3. 启动服务(会自动构建镜像)
|
||||
# 3. 启动服务
|
||||
docker-compose up -d
|
||||
|
||||
# 4. 访问应用
|
||||
# 打开浏览器访问 http://localhost:8000
|
||||
```
|
||||
|
||||
### 方式二:本地开发
|
||||
|
||||
#### 后端设置
|
||||
### 使用 Docker Hub 镜像
|
||||
|
||||
```bash
|
||||
# 拉取最新镜像
|
||||
docker pull mumujie/mumuainovel:latest
|
||||
|
||||
# 使用 docker-compose.yml 启动
|
||||
docker-compose up -d
|
||||
|
||||
# 查看日志
|
||||
docker-compose logs -f
|
||||
|
||||
# 更新到最新版本
|
||||
docker-compose pull
|
||||
docker-compose up -d
|
||||
```
|
||||
|
||||
### 本地开发
|
||||
|
||||
#### 后端
|
||||
|
||||
```bash
|
||||
# 进入后端目录
|
||||
cd backend
|
||||
|
||||
# 创建虚拟环境
|
||||
python -m venv .venv
|
||||
|
||||
# 激活虚拟环境
|
||||
# Windows:
|
||||
.venv\Scripts\activate
|
||||
# Linux/Mac:
|
||||
source .venv/bin/activate
|
||||
|
||||
# 安装依赖
|
||||
source .venv/bin/activate # Windows: .venv\Scripts\activate
|
||||
pip install -r requirements.txt
|
||||
|
||||
# 配置环境变量
|
||||
# 配置 .env 文件
|
||||
cp .env.example .env
|
||||
# 编辑 .env 文件,填入你的配置
|
||||
|
||||
# 启动后端服务
|
||||
# 启动后端
|
||||
python -m uvicorn app.main:app --host 0.0.0.0 --port 8000 --reload
|
||||
```
|
||||
|
||||
#### 前端设置
|
||||
#### 前端
|
||||
|
||||
```bash
|
||||
# 进入前端目录
|
||||
cd frontend
|
||||
|
||||
# 安装依赖
|
||||
npm install
|
||||
|
||||
# 开发模式(需要后端已启动)
|
||||
npm run dev
|
||||
|
||||
# 或构建生产版本
|
||||
npm run build
|
||||
npm run dev # 开发模式
|
||||
npm run build # 生产构建
|
||||
```
|
||||
|
||||
## 🐳 部署方式
|
||||
## ⚙️ 配置说明
|
||||
|
||||
### Docker Compose 部署(PostgreSQL)
|
||||
### 必需配置
|
||||
|
||||
**推荐生产环境使用**,提供更好的性能和并发支持。
|
||||
|
||||
#### 快速启动
|
||||
创建 `.env` 文件:
|
||||
|
||||
```bash
|
||||
# 1. 克隆项目
|
||||
git clone https://github.com/xiamuceer-j/MuMuAINovel.git
|
||||
cd MuMuAINovel
|
||||
# PostgreSQL 数据库(必需)
|
||||
DATABASE_URL=postgresql+asyncpg://mumuai:your_password@postgres:5432/mumuai_novel
|
||||
POSTGRES_PASSWORD=your_secure_password
|
||||
|
||||
# 2. 配置环境变量
|
||||
cp backend/.env.example .env
|
||||
# 编辑 .env 文件,设置必要的配置:
|
||||
# - POSTGRES_PASSWORD(数据库密码)
|
||||
# - OPENAI_API_KEY(AI服务密钥)
|
||||
# - 其他可选配置
|
||||
|
||||
# 3. 启动服务(包含PostgreSQL)
|
||||
docker-compose up -d
|
||||
|
||||
# 4. 查看服务状态
|
||||
docker-compose ps
|
||||
|
||||
# 5. 查看日志
|
||||
docker-compose logs -f
|
||||
|
||||
# 6. 访问应用
|
||||
# 打开浏览器访问 http://localhost:8000
|
||||
```
|
||||
|
||||
#### 环境变量配置
|
||||
|
||||
创建 `.env` 文件并配置:
|
||||
|
||||
```bash
|
||||
# PostgreSQL数据库密码(必须设置)
|
||||
POSTGRES_PASSWORD=your_secure_password_here
|
||||
|
||||
# AI服务配置(必须设置)
|
||||
OPENAI_API_KEY=your_openai_api_key
|
||||
# AI 服务(至少配置一个)
|
||||
OPENAI_API_KEY=your_openai_key
|
||||
OPENAI_BASE_URL=https://api.openai.com/v1
|
||||
DEFAULT_AI_PROVIDER=openai
|
||||
DEFAULT_MODEL=gpt-4
|
||||
DEFAULT_MODEL=gpt-4o-mini
|
||||
|
||||
# 本地账户登录(可选)
|
||||
# 本地账户登录
|
||||
LOCAL_AUTH_ENABLED=true
|
||||
LOCAL_AUTH_USERNAME=admin
|
||||
LOCAL_AUTH_PASSWORD=admin123
|
||||
|
||||
# 其他配置见 backend/.env.example
|
||||
LOCAL_AUTH_PASSWORD=your_password
|
||||
```
|
||||
|
||||
#### 服务说明
|
||||
|
||||
- **postgres**: PostgreSQL 18 数据库
|
||||
- 端口:5432
|
||||
- 数据持久化:`./postgres_data`
|
||||
- 已优化配置,支持80-150并发用户
|
||||
|
||||
- **mumuainovel**: 主应用服务
|
||||
- 端口:8000
|
||||
- 自动等待数据库就绪
|
||||
- 日志持久化:`./logs`
|
||||
|
||||
详细部署指南请参考:[Docker + PostgreSQL 部署文档](docs/docker-postgres-deployment.md)
|
||||
|
||||
### Docker Compose 部署(SQLite)
|
||||
|
||||
适合个人使用或小团队,配置更简单。
|
||||
|
||||
#### 使用 Docker Hub 镜像
|
||||
|
||||
项目已发布到 Docker Hub,可直接拉取使用:
|
||||
### 可选配置
|
||||
|
||||
```bash
|
||||
# 查看可用版本
|
||||
docker pull mumujie/mumuainovel:latest
|
||||
# Gemini
|
||||
GEMINI_API_KEY=your_gemini_key
|
||||
|
||||
# Claude
|
||||
ANTHROPIC_API_KEY=your_claude_key
|
||||
|
||||
# LinuxDO OAuth
|
||||
LINUXDO_CLIENT_ID=your_client_id
|
||||
LINUXDO_CLIENT_SECRET=your_client_secret
|
||||
LINUXDO_REDIRECT_URI=http://localhost:8000/api/auth/callback
|
||||
|
||||
# PostgreSQL 连接池(高并发优化)
|
||||
DATABASE_POOL_SIZE=30
|
||||
DATABASE_MAX_OVERFLOW=20
|
||||
```
|
||||
|
||||
### 中转 API 配置
|
||||
|
||||
支持所有 OpenAI 兼容格式的中转服务:
|
||||
|
||||
```bash
|
||||
# New API 示例
|
||||
OPENAI_API_KEY=sk-xxxxxxxx
|
||||
OPENAI_BASE_URL=https://api.new-api.com/v1
|
||||
|
||||
# 其他中转服务
|
||||
OPENAI_BASE_URL=https://your-proxy-service.com/v1
|
||||
```
|
||||
|
||||
## 🐳 Docker 部署详情
|
||||
|
||||
### 服务架构
|
||||
|
||||
- **postgres**: PostgreSQL 18 数据库
|
||||
- 端口: 5432
|
||||
- 数据持久化: `./postgres_data`
|
||||
- 优化配置: 支持 80-150 并发用户
|
||||
|
||||
- **mumuainovel**: 主应用服务
|
||||
- 端口: 8000
|
||||
- 日志目录: `./logs`
|
||||
- 自动等待数据库就绪
|
||||
|
||||
### 常用命令
|
||||
|
||||
```bash
|
||||
# 启动服务
|
||||
docker-compose up -d
|
||||
|
||||
# 查看状态
|
||||
docker-compose ps
|
||||
|
||||
# 查看日志
|
||||
docker-compose logs -f
|
||||
|
||||
@@ -208,258 +196,22 @@ docker-compose down
|
||||
# 重启服务
|
||||
docker-compose restart
|
||||
|
||||
# 更新到最新版本
|
||||
docker-compose pull
|
||||
docker-compose up -d
|
||||
# 查看资源使用
|
||||
docker stats
|
||||
```
|
||||
|
||||
#### Docker Compose 配置文件示例
|
||||
### 数据持久化
|
||||
|
||||
使用 Docker Hub 镜像的完整配置:
|
||||
- `./postgres_data` - PostgreSQL 数据库文件
|
||||
- `./logs` - 应用日志文件
|
||||
|
||||
### 端口配置
|
||||
|
||||
修改 `docker-compose.yml` 中的端口映射:
|
||||
|
||||
```yaml
|
||||
services:
|
||||
ai-story:
|
||||
image: mumujie/mumuainovel:latest
|
||||
container_name: mumuainovel
|
||||
ports:
|
||||
- "8800:8000" # 宿主机端口:容器端口
|
||||
volumes:
|
||||
# 持久化数据库和日志
|
||||
- ./data:/app/data
|
||||
- ./logs:/app/logs
|
||||
# 挂载环境变量文件
|
||||
- ./.env:/app/.env:ro
|
||||
environment:
|
||||
- APP_NAME=mumuainovel
|
||||
- APP_VERSION=1.0.0
|
||||
- APP_HOST=0.0.0.0
|
||||
- APP_PORT=8000
|
||||
- DEBUG=false
|
||||
# 其他环境变量会从 .env 文件自动加载
|
||||
restart: unless-stopped
|
||||
healthcheck:
|
||||
test: ["CMD", "python", "-c", "import urllib.request; urllib.request.urlopen('http://localhost:8000/health')"]
|
||||
interval: 30s
|
||||
timeout: 10s
|
||||
retries: 3
|
||||
start_period: 10s
|
||||
networks:
|
||||
- ai-story-network
|
||||
|
||||
networks:
|
||||
ai-story-network:
|
||||
driver: bridge
|
||||
```
|
||||
|
||||
### 生产环境部署建议
|
||||
|
||||
#### 1. 环境变量配置
|
||||
|
||||
**必需配置**:
|
||||
- `OPENAI_API_KEY` 或 `GEMINI_API_KEY`:至少配置一个 AI 服务
|
||||
- `LOCAL_AUTH_PASSWORD`:修改为强密码
|
||||
|
||||
**推荐配置**:
|
||||
- `OPENAI_BASE_URL`:如果使用中转 API,修改为中转服务地址
|
||||
- `DEFAULT_AI_PROVIDER`:根据你的 API Key 选择 `openai`、`gemini` 或 `anthropic`
|
||||
- `DEFAULT_MODEL`:选择合适的模型(如 `gpt-4o-mini`、`gemini-2.0-flash-exp`)
|
||||
|
||||
#### 2. 数据持久化
|
||||
|
||||
**PostgreSQL部署**:
|
||||
- `./postgres_data`:PostgreSQL 数据库文件
|
||||
- `./logs`:应用日志文件
|
||||
|
||||
**SQLite部署**:
|
||||
- `./data`:SQLite 数据库文件
|
||||
- `./logs`:应用日志文件
|
||||
|
||||
#### 3. 端口配置
|
||||
|
||||
默认端口映射:`8800:8000`
|
||||
- 宿主机端口:`8800`(可自定义修改)
|
||||
- 容器内端口:`8000`(固定,不要修改)
|
||||
|
||||
访问地址:`http://your-server-ip:8800`
|
||||
|
||||
|
||||
配置后记得更新 `.env` 中的 `LINUXDO_REDIRECT_URI` 和 `FRONTEND_URL`。
|
||||
|
||||
#### 5. 资源限制(可选)
|
||||
|
||||
在 `docker-compose.yml` 中添加资源限制:
|
||||
|
||||
```yaml
|
||||
services:
|
||||
ai-story:
|
||||
# ... 其他配置
|
||||
deploy:
|
||||
resources:
|
||||
limits:
|
||||
cpus: '2.0'
|
||||
memory: 2G
|
||||
reservations:
|
||||
cpus: '0.5'
|
||||
memory: 512M
|
||||
```
|
||||
|
||||
### 端口说明
|
||||
|
||||
- **默认端口**:`8800`(宿主机)→ `8000`(容器)
|
||||
- **可自定义**:修改 docker-compose.yml 中的 `ports` 配置
|
||||
- **健康检查**:容器内部使用 `8000` 端口进行健康检查
|
||||
|
||||
## ⚙️ 配置说明
|
||||
|
||||
### 数据库选择
|
||||
|
||||
项目支持两种数据库:
|
||||
|
||||
```bash
|
||||
# .env 配置
|
||||
DATABASE_URL=postgresql+asyncpg://mumuai:password@postgres:5432/mumuai_novel
|
||||
```
|
||||
|
||||
```bash
|
||||
# .env 配置
|
||||
DATABASE_URL=sqlite+aiosqlite:///data/ai_story.db
|
||||
```
|
||||
|
||||
### 环境变量
|
||||
|
||||
创建 `.env` 文件并配置以下变量:
|
||||
|
||||
```bash
|
||||
# ===== 数据库配置 =====
|
||||
# PostgreSQL(生产环境推荐)
|
||||
DATABASE_URL=postgresql+asyncpg://mumuai:password@postgres:5432/mumuai_novel
|
||||
POSTGRES_PASSWORD=your_secure_password_here
|
||||
|
||||
# 或使用 SQLite(开发环境)
|
||||
# DATABASE_URL=sqlite+aiosqlite:///data/ai_story.db
|
||||
|
||||
# ===== AI 服务配置(必填)=====
|
||||
# OpenAI 配置(支持官方API和中转API)
|
||||
OPENAI_API_KEY=your_openai_key_here
|
||||
OPENAI_BASE_URL=https://api.openai.com/v1
|
||||
|
||||
# Anthropic 配置
|
||||
# ANTHROPIC_API_KEY=your_anthropic_key_here
|
||||
# ANTHROPIC_BASE_URL=https://api.anthropic.com
|
||||
|
||||
# 中转API配置示例(使用OpenAI格式)
|
||||
# New API 中转服务
|
||||
# OPENAI_API_KEY=your_newapi_key_here
|
||||
# OPENAI_BASE_URL=https://api.new-api.com/v1
|
||||
|
||||
# 默认 AI 提供商和模型
|
||||
DEFAULT_AI_PROVIDER=openai
|
||||
DEFAULT_MODEL=gpt-4o-mini
|
||||
DEFAULT_TEMPERATURE=0.8
|
||||
DEFAULT_MAX_TOKENS=32000
|
||||
|
||||
# ===== 应用配置 =====
|
||||
APP_NAME=MuMuAINovel
|
||||
APP_VERSION=1.0.0
|
||||
APP_HOST=0.0.0.0
|
||||
APP_PORT=8000
|
||||
DEBUG=false
|
||||
|
||||
# ===== LinuxDO OAuth 配置(可选)=====
|
||||
LINUXDO_CLIENT_ID=your_client_id_here
|
||||
LINUXDO_CLIENT_SECRET=your_client_secret_here
|
||||
LINUXDO_REDIRECT_URI=http://localhost:8000/api/auth/callback
|
||||
FRONTEND_URL=http://localhost:8000
|
||||
|
||||
# ===== 本地账户登录配置 =====
|
||||
LOCAL_AUTH_ENABLED=true
|
||||
LOCAL_AUTH_USERNAME=admin
|
||||
LOCAL_AUTH_PASSWORD=your_secure_password_here
|
||||
LOCAL_AUTH_DISPLAY_NAME=管理员
|
||||
|
||||
# 会话配置
|
||||
# 会话过期时间(分钟),默认120分钟(2小时)
|
||||
SESSION_EXPIRE_MINUTES=120
|
||||
# 会话刷新阈值(分钟),剩余时间少于此值时可刷新,默认30分钟
|
||||
SESSION_REFRESH_THRESHOLD_MINUTES=30
|
||||
|
||||
# ===== CORS 配置(生产环境)=====
|
||||
# CORS_ORIGINS=https://your-domain.com,https://www.your-domain.com
|
||||
```
|
||||
|
||||
### AI 模型配置
|
||||
|
||||
项目支持多个 AI 提供商,你可以根据需要配置:
|
||||
|
||||
| 提供商 | 推荐模型 | 用途 |
|
||||
|--------|---------|------|
|
||||
| OpenAI | gpt-4, gpt-3.5-turbo | 高质量文本生成 |
|
||||
| Anthropic | claude-3-opus, claude-3-sonnet | 长文本创作 |
|
||||
|
||||
#### 使用中转API服务
|
||||
|
||||
如果你无法直接访问 OpenAI 官方 API,或者想使用更经济实惠的中转服务,本项目完全支持各种 OpenAI 兼容格式的中转 API:
|
||||
|
||||
##### 配置方法
|
||||
|
||||
只需修改 `.env` 文件中的两个参数:
|
||||
|
||||
```bash
|
||||
# 1. 填入中转服务提供的 API Key
|
||||
OPENAI_API_KEY=your_api_key_from_proxy_service
|
||||
|
||||
# 2. 修改 Base URL 为中转服务的地址
|
||||
OPENAI_BASE_URL=https://your-proxy-service.com/v1
|
||||
```
|
||||
|
||||
##### 常见中转服务配置示例
|
||||
|
||||
**New API**
|
||||
```bash
|
||||
OPENAI_API_KEY=sk-xxxxxxxxxxxxxxxx
|
||||
OPENAI_BASE_URL=https://api.new-api.com/v1
|
||||
```
|
||||
|
||||
##### 注意事项
|
||||
|
||||
- ✅ 所有支持 OpenAI 接口格式的服务都可以使用
|
||||
- ✅ 确保中转服务的 Base URL 以 `/v1` 结尾
|
||||
- ✅ 根据中转服务支持的模型,修改 `DEFAULT_MODEL` 参数
|
||||
- ⚠️ 不同中转服务的模型名称可能不同,请参考服务商文档
|
||||
- ⚠️ 部分中转服务可能对请求频率或并发有限制
|
||||
|
||||
##### 推荐的中转服务
|
||||
|
||||
如果你需要中转服务,以下是一些常见选择:
|
||||
|
||||
1. **New API** - 开源的 API 分发系统,支持多种模型
|
||||
2. **API2D** - 国内稳定的 API 中转服务
|
||||
3. **OpenAI-SB** - 提供多种 AI 模型的中转
|
||||
4. **自建服务** - 使用 One API 或 New API 自行搭建
|
||||
|
||||
> 💡 提示:使用中转服务时,请确保服务提供商的可靠性和数据安全性
|
||||
|
||||
### 登录方式配置
|
||||
|
||||
#### 本地账户登录(默认启用)
|
||||
|
||||
适合个人使用或小型团队:
|
||||
|
||||
```bash
|
||||
LOCAL_AUTH_ENABLED=true
|
||||
LOCAL_AUTH_USERNAME=admin
|
||||
LOCAL_AUTH_PASSWORD=your_password
|
||||
```
|
||||
|
||||
#### LinuxDO OAuth 登录
|
||||
|
||||
适合需要社区集成的场景,需要在 [LinuxDO](https://linux.do) 注册 OAuth 应用:
|
||||
|
||||
```bash
|
||||
LINUXDO_CLIENT_ID=your_client_id
|
||||
LINUXDO_CLIENT_SECRET=your_client_secret
|
||||
LINUXDO_REDIRECT_URI=http://your-domain:8000/api/auth/callback
|
||||
- "8800:8000" # 宿主机:容器
|
||||
```
|
||||
|
||||
## 📁 项目结构
|
||||
@@ -469,93 +221,42 @@ MuMuAINovel/
|
||||
├── backend/ # 后端服务
|
||||
│ ├── app/
|
||||
│ │ ├── api/ # API 路由
|
||||
│ │ │ ├── auth.py # 认证接口
|
||||
│ │ │ ├── projects.py # 项目管理
|
||||
│ │ │ ├── chapters.py # 章节管理
|
||||
│ │ │ ├── characters.py # 角色管理
|
||||
│ │ │ ├── wizard_stream.py # 向导流式生成
|
||||
│ │ │ └── ...
|
||||
│ │ ├── models/ # 数据模型
|
||||
│ │ ├── schemas/ # Pydantic 模型
|
||||
│ │ ├── services/ # 业务逻辑
|
||||
│ │ │ ├── ai_service.py # AI 服务封装
|
||||
│ │ │ └── oauth_service.py # OAuth 服务
|
||||
│ │ ├── middleware/ # 中间件
|
||||
│ │ ├── utils/ # 工具函数
|
||||
│ │ ├── config.py # 配置管理
|
||||
│ │ ├── database.py # 数据库连接
|
||||
│ │ └── main.py # 应用入口
|
||||
│ ├── data/ # 数据存储目录
|
||||
│ ├── static/ # 前端静态文件(构建后)
|
||||
│ ├── requirements.txt # Python 依赖
|
||||
│ └── .env.example # 环境变量示例
|
||||
│ ├── scripts/ # 工具脚本
|
||||
│ └── requirements.txt # Python 依赖
|
||||
├── frontend/ # 前端应用
|
||||
│ ├── src/
|
||||
│ │ ├── pages/ # 页面组件
|
||||
│ │ │ ├── ProjectList.tsx # 项目列表
|
||||
│ │ │ ├── ProjectWizardNew.tsx # 创建向导
|
||||
│ │ │ ├── Chapters.tsx # 章节管理
|
||||
│ │ │ ├── Characters.tsx # 角色管理
|
||||
│ │ │ └── ...
|
||||
│ │ ├── components/ # 通用组件
|
||||
│ │ ├── services/ # API 服务
|
||||
│ │ ├── store/ # 状态管理(Zustand)
|
||||
│ │ ├── types/ # TypeScript 类型
|
||||
│ │ └── utils/ # 工具函数
|
||||
│ ├── package.json
|
||||
│ └── vite.config.ts
|
||||
│ │ └── store/ # 状态管理
|
||||
│ └── package.json
|
||||
├── docker-compose.yml # Docker Compose 配置
|
||||
├── Dockerfile # Docker 镜像构建
|
||||
└── README.md # 项目说明文档
|
||||
└── README.md
|
||||
```
|
||||
|
||||
## 🛠️ 技术栈
|
||||
|
||||
### 后端
|
||||
**后端**: FastAPI • PostgreSQL • SQLAlchemy • OpenAI/Claude/Gemini SDK
|
||||
|
||||
- **框架**:FastAPI 0.109.0
|
||||
- **数据库**:PostgreSQL / SQLite + SQLAlchemy(异步)
|
||||
- **AI 集成**:OpenAI、Anthropic、Google Gemini SDK
|
||||
- **认证**:LinuxDO OAuth2、本地账户
|
||||
- **日志**:Python logging + 文件轮转
|
||||
|
||||
### 前端
|
||||
|
||||
- **框架**:React 18.3 + TypeScript
|
||||
- **UI 库**:Ant Design 5.27
|
||||
- **路由**:React Router 6.28
|
||||
- **状态管理**:Zustand 5.0
|
||||
- **HTTP 客户端**:Axios
|
||||
- **构建工具**:Vite 7.1
|
||||
**前端**: React 18 • TypeScript • Ant Design • Zustand • Vite
|
||||
|
||||
## 📖 使用指南
|
||||
|
||||
### 创建第一个小说项目
|
||||
|
||||
1. **登录系统**
|
||||
- 使用本地账户或 LinuxDO 账户登录
|
||||
|
||||
2. **创建项目**
|
||||
- 点击"创建项目"按钮
|
||||
- 选择"使用向导创建"或"手动创建"
|
||||
|
||||
3. **使用向导(推荐)**
|
||||
- 输入小说基本信息(标题、类型、背景等)
|
||||
- AI 自动生成大纲、角色和世界观
|
||||
- 实时查看生成进度
|
||||
|
||||
4. **编辑和完善**
|
||||
- 在项目详情页查看和编辑大纲
|
||||
- 管理角色和人物关系
|
||||
- 生成和编辑章节内容
|
||||
|
||||
1. **登录系统** - 使用本地账户或 LinuxDO 账户
|
||||
2. **创建项目** - 选择"使用向导创建"
|
||||
3. **AI 生成** - 输入基本信息,AI 自动生成大纲和角色
|
||||
4. **编辑完善** - 管理角色关系,生成和编辑章节
|
||||
|
||||
### API 文档
|
||||
|
||||
应用启动后,可访问自动生成的 API 文档:
|
||||
|
||||
- Swagger UI:`http://localhost:8000/docs`
|
||||
- ReDoc:`http://localhost:8000/redoc`
|
||||
- Swagger UI: `http://localhost:8000/docs`
|
||||
- ReDoc: `http://localhost:8000/redoc`
|
||||
|
||||
## 🤝 贡献
|
||||
|
||||
@@ -569,38 +270,32 @@ MuMuAINovel/
|
||||
|
||||
## 📝 许可证
|
||||
|
||||
本项目采用 [GNU General Public License v3.0](https://www.gnu.org/licenses/gpl-3.0.html) 开源协议
|
||||
本项目采用 [GNU General Public License v3.0](LICENSE)
|
||||
|
||||
**这意味着:**
|
||||
|
||||
- ✅ **可以** - 自由使用、复制、修改和分发本项目
|
||||
- ✅ **可以** - 用于商业目的
|
||||
- ✅ **可以** - 用于个人学习和研究
|
||||
- 📝 **必须** - 开源你的修改版本
|
||||
- 📝 **必须** - 保留原作者版权声明
|
||||
- 📝 **必须** - 以相同的 GPL v3 协议发布衍生作品
|
||||
|
||||
详见 [LICENSE](LICENSE) 文件
|
||||
**GPL v3 意味着:**
|
||||
- ✅ 可自由使用、修改和分发
|
||||
- ✅ 可用于商业目的
|
||||
- 📝 必须开源修改版本
|
||||
- 📝 必须保留原作者版权
|
||||
- 📝 衍生作品必须使用 GPL v3 协议
|
||||
|
||||
## 🙏 致谢
|
||||
|
||||
- [FastAPI](https://fastapi.tiangolo.com/) - 现代化的 Python Web 框架
|
||||
- [React](https://react.dev/) - 用户界面构建库
|
||||
- [Ant Design](https://ant.design/) - 企业级 UI 设计语言
|
||||
- [OpenAI](https://openai.com/) / [Anthropic](https://www.anthropic.com/) - AI 模型提供商
|
||||
- [FastAPI](https://fastapi.tiangolo.com/) - Python Web 框架
|
||||
- [React](https://react.dev/) - 前端框架
|
||||
- [Ant Design](https://ant.design/) - UI 组件库
|
||||
- [PostgreSQL](https://www.postgresql.org/) - 数据库
|
||||
|
||||
## 📧 联系方式
|
||||
|
||||
如有问题或建议,欢迎通过以下方式联系:
|
||||
|
||||
- 提交 [Issue](https://github.com/yourusername/MuMuAINovel/issues)
|
||||
- Linux DO [LD](https://linux.do/t/topic/1100112)
|
||||
- 提交 [Issue](https://github.com/xiamuceer-j/MuMuAINovel/issues)
|
||||
- Linux DO [讨论](https://linux.do/t/topic/1100112)
|
||||
|
||||
---
|
||||
|
||||
<div align="center">
|
||||
|
||||
**如果这个项目对你有帮助,请给个 ⭐️ Star 支持一下!**
|
||||
**如果这个项目对你有帮助,请给个 ⭐️ Star!**
|
||||
|
||||
Made with ❤️
|
||||
|
||||
|
||||
+37
-46
@@ -11,19 +11,21 @@ APP_NAME=MuMuAINovel
|
||||
APP_VERSION=1.0.0
|
||||
APP_HOST=0.0.0.0
|
||||
APP_PORT=8000
|
||||
DEBUG=True
|
||||
DEBUG=false
|
||||
TZ=Asia/Shanghai
|
||||
|
||||
# ==========================================
|
||||
# 数据库配置
|
||||
# PostgreSQL 数据库配置
|
||||
# ==========================================
|
||||
|
||||
# 选项1: PostgreSQL(生产环境推荐)
|
||||
# DATABASE_URL=postgresql+asyncpg://username:password@localhost:5432/database_name
|
||||
# 示例:
|
||||
# DATABASE_URL=postgresql+asyncpg://mumuai:your_password@localhost:5432/mumuai_novel
|
||||
# PostgreSQL 连接信息
|
||||
POSTGRES_DB=mumuai_novel
|
||||
POSTGRES_USER=mumuai
|
||||
POSTGRES_PASSWORD=your_secure_password_here
|
||||
POSTGRES_PORT=5432
|
||||
|
||||
# 选项2: SQLite(开发环境,默认)
|
||||
DATABASE_URL=sqlite+aiosqlite:///data/ai_story.db
|
||||
# 数据库连接 URL(Docker 部署时自动生成)
|
||||
DATABASE_URL=postgresql+asyncpg://mumuai:your_secure_password_here@localhost:5432/mumuai_novel
|
||||
|
||||
# PostgreSQL 连接池配置(优化后,支持80-150并发用户)
|
||||
DATABASE_POOL_SIZE=30 # 核心连接数(默认30,小团队可用20)
|
||||
@@ -37,21 +39,23 @@ DATABASE_POOL_USE_LIFO=True # 使用LIFO策略提高连接复用率
|
||||
DATABASE_SESSION_MAX_ACTIVE=50 # 活跃会话警告阈值
|
||||
DATABASE_SESSION_LEAK_THRESHOLD=100 # 会话泄漏严重告警阈值
|
||||
|
||||
# SQLite 性能优化配置(仅在使用SQLite时生效)
|
||||
SQLITE_CACHE_SIZE_MB=128 # SQLite缓存大小(MB),默认128
|
||||
SQLITE_MMAP_SIZE_MB=256 # 内存映射I/O大小(MB),默认256
|
||||
SQLITE_WAL_AUTOCHECKPOINT=1000 # WAL自动检查点间隔
|
||||
|
||||
# 数据库监控配置
|
||||
DATABASE_ENABLE_SLOW_QUERY_LOG=True # 启用慢查询日志
|
||||
DATABASE_SLOW_QUERY_THRESHOLD=1.0 # 慢查询阈值(秒)
|
||||
DATABASE_ENABLE_METRICS=True # 启用性能指标收集
|
||||
|
||||
# ==========================================
|
||||
# 代理配置(可选)
|
||||
# ==========================================
|
||||
# HTTP_PROXY=http://your-proxy:port
|
||||
# HTTPS_PROXY=http://your-proxy:port
|
||||
# NO_PROXY=localhost,127.0.0.1
|
||||
|
||||
# ==========================================
|
||||
# 日志配置
|
||||
# ==========================================
|
||||
LOG_LEVEL=INFO
|
||||
LOG_TO_FILE=True
|
||||
LOG_TO_FILE=true
|
||||
LOG_FILE_PATH=logs/app.log
|
||||
LOG_MAX_BYTES=10485760
|
||||
LOG_BACKUP_COUNT=30
|
||||
@@ -62,18 +66,12 @@ LOG_BACKUP_COUNT=30
|
||||
CORS_ORIGINS=["http://localhost:8000","http://127.0.0.1:8000"]
|
||||
|
||||
# ==========================================
|
||||
# AI服务配置
|
||||
# AI 服务配置(至少配置一个)
|
||||
# ==========================================
|
||||
|
||||
# OpenAI 配置
|
||||
OPENAI_API_KEY=your_openai_api_key_here
|
||||
OPENAI_BASE_URL=https://api.openai.com/v1
|
||||
# 或使用兼容的API服务(如DeepSeek)
|
||||
# OPENAI_BASE_URL=https://api.deepseek.com/v1
|
||||
|
||||
# Gemini配置(可选)
|
||||
# GEMINI_API_KEY=your_gemini_api_key_here
|
||||
# GEMINI_BASE_URL=https://generativelanguage.googleapis.com
|
||||
|
||||
# Anthropic 配置(可选)
|
||||
# ANTHROPIC_API_KEY=your_anthropic_api_key_here
|
||||
@@ -81,29 +79,29 @@ OPENAI_BASE_URL=https://api.openai.com/v1
|
||||
|
||||
# 默认 AI 配置
|
||||
DEFAULT_AI_PROVIDER=openai
|
||||
DEFAULT_MODEL=gpt-4
|
||||
DEFAULT_MODEL=gpt-4o-mini
|
||||
DEFAULT_TEMPERATURE=0.7
|
||||
DEFAULT_MAX_TOKENS=2000
|
||||
|
||||
# ==========================================
|
||||
# LinuxDO OAuth2 配置(可选)
|
||||
# LinuxDO OAuth 配置(可选)
|
||||
# ==========================================
|
||||
# LINUXDO_CLIENT_ID=your_client_id
|
||||
# LINUXDO_CLIENT_SECRET=your_client_secret
|
||||
# LINUXDO_CLIENT_ID=your_client_id_here
|
||||
# LINUXDO_CLIENT_SECRET=your_client_secret_here
|
||||
# LINUXDO_REDIRECT_URI=http://localhost:8000/api/auth/callback
|
||||
|
||||
# 前端 URL(OAuth 回调后重定向)
|
||||
FRONTEND_URL=http://localhost:8000
|
||||
|
||||
# 初始管理员(LinuxDO user_id)
|
||||
# INITIAL_ADMIN_LINUXDO_ID=12345
|
||||
# INITIAL_ADMIN_LINUXDO_ID=your_linuxdo_user_id
|
||||
|
||||
# ==========================================
|
||||
# 本地账户登录配置
|
||||
# ==========================================
|
||||
LOCAL_AUTH_ENABLED=True
|
||||
LOCAL_AUTH_ENABLED=true
|
||||
LOCAL_AUTH_USERNAME=admin
|
||||
LOCAL_AUTH_PASSWORD=admin123
|
||||
LOCAL_AUTH_PASSWORD=your_secure_password_here
|
||||
LOCAL_AUTH_DISPLAY_NAME=本地管理员
|
||||
|
||||
# ==========================================
|
||||
@@ -113,28 +111,21 @@ SESSION_EXPIRE_MINUTES=120
|
||||
SESSION_REFRESH_THRESHOLD_MINUTES=30
|
||||
|
||||
# ==========================================
|
||||
# 部署配置说明
|
||||
# 部署配置示例
|
||||
# ==========================================
|
||||
|
||||
# 生产环境 PostgreSQL 配置示例(50-100并发用户):
|
||||
# DATABASE_URL=postgresql+asyncpg://mumuai:SecurePassword123@db.example.com:5432/mumuai_prod
|
||||
# DATABASE_POOL_SIZE=30
|
||||
# DATABASE_MAX_OVERFLOW=20
|
||||
# DATABASE_POOL_TIMEOUT=60
|
||||
# DATABASE_POOL_RECYCLE=1800
|
||||
# DATABASE_SESSION_MAX_ACTIVE=50
|
||||
# DEBUG=False
|
||||
# LOG_LEVEL=WARNING
|
||||
|
||||
# 高并发环境 PostgreSQL 配置示例(100+并发用户):
|
||||
# DATABASE_URL=postgresql+asyncpg://mumuai:SecurePassword123@db.example.com:5432/mumuai_prod
|
||||
# Docker 生产环境配置:
|
||||
# POSTGRES_PASSWORD=your_very_secure_password
|
||||
# DATABASE_POOL_SIZE=40
|
||||
# DATABASE_MAX_OVERFLOW=30
|
||||
# DATABASE_SESSION_MAX_ACTIVE=80
|
||||
# DATABASE_SESSION_LEAK_THRESHOLD=150
|
||||
# DEBUG=false
|
||||
# LOG_LEVEL=WARNING
|
||||
|
||||
# Docker 部署配置示例:
|
||||
# DATABASE_URL=postgresql+asyncpg://mumuai:password@postgres:5432/mumuai_novel
|
||||
# OPENAI_BASE_URL=https://api.openai.com/v1
|
||||
# 外网访问配置:
|
||||
# FRONTEND_URL=https://your-domain.com
|
||||
# LINUXDO_REDIRECT_URI=https://your-domain.com/api/auth/callback
|
||||
# APP_PORT=8000
|
||||
|
||||
# 中转 API 配置示例:
|
||||
# OPENAI_BASE_URL=https://api.new-api.com/v1
|
||||
# DEFAULT_MODEL=gpt-4o-mini
|
||||
+5
-14
@@ -13,15 +13,11 @@ DATA_DIR.mkdir(exist_ok=True)
|
||||
# 配置模块使用标准logging(在logger.py初始化之前)
|
||||
config_logger = logging.getLogger(__name__)
|
||||
|
||||
# 数据库配置:支持PostgreSQL和SQLite
|
||||
# 优先使用环境变量DATABASE_URL,否则使用SQLite
|
||||
DB_FILE = DATA_DIR / "ai_story.db"
|
||||
DEFAULT_SQLITE_URL = f"sqlite+aiosqlite:///{str(DB_FILE.absolute()).replace(chr(92), '/')}"
|
||||
# 数据库配置:PostgreSQL
|
||||
# 从环境变量获取数据库URL
|
||||
DATABASE_URL = os.getenv("DATABASE_URL", "postgresql+asyncpg://mumuai:password@localhost:5432/mumuai_novel")
|
||||
|
||||
# 从环境变量获取数据库URL,如果未设置则使用SQLite
|
||||
DATABASE_URL = os.getenv("DATABASE_URL", DEFAULT_SQLITE_URL)
|
||||
|
||||
config_logger.debug(f"数据库类型: {'PostgreSQL' if 'postgresql' in DATABASE_URL else 'SQLite'}")
|
||||
config_logger.debug(f"数据库类型: PostgreSQL")
|
||||
config_logger.debug(f"数据库URL: {DATABASE_URL}")
|
||||
|
||||
class Settings(BaseSettings):
|
||||
@@ -44,7 +40,7 @@ class Settings(BaseSettings):
|
||||
# CORS配置
|
||||
cors_origins: list[str] = ["http://localhost:8000", "http://127.0.0.1:8000"]
|
||||
|
||||
# 数据库配置 - 支持PostgreSQL和SQLite
|
||||
# 数据库配置 - PostgreSQL
|
||||
database_url: str = DATABASE_URL
|
||||
|
||||
# PostgreSQL连接池配置(优化后支持80-150并发用户)
|
||||
@@ -59,11 +55,6 @@ class Settings(BaseSettings):
|
||||
database_session_max_active: int = 50 # 活跃会话警告阈值(从100降低到50)
|
||||
database_session_leak_threshold: int = 100 # 会话泄漏严重告警阈值
|
||||
|
||||
# SQLite优化配置
|
||||
sqlite_cache_size_mb: int = 128 # SQLite缓存大小MB(从64提升到128)
|
||||
sqlite_mmap_size_mb: int = 256 # 内存映射I/O大小MB
|
||||
sqlite_wal_autocheckpoint: int = 1000 # WAL自动检查点间隔
|
||||
|
||||
# 数据库监控配置
|
||||
database_enable_slow_query_log: bool = True # 启用慢查询日志
|
||||
database_slow_query_threshold: float = 1.0 # 慢查询阈值(秒)
|
||||
|
||||
+4
-66
@@ -1,11 +1,10 @@
|
||||
"""数据库连接和会话管理 - 支持多用户数据隔离"""
|
||||
"""数据库连接和会话管理 - PostgreSQL 多用户数据隔离"""
|
||||
import asyncio
|
||||
from typing import Dict, Any
|
||||
from datetime import datetime
|
||||
from sqlalchemy import select, text
|
||||
from sqlalchemy.ext.asyncio import create_async_engine, AsyncSession, async_sessionmaker
|
||||
from sqlalchemy.orm import declarative_base
|
||||
from sqlalchemy.pool import StaticPool
|
||||
from fastapi import Request, HTTPException
|
||||
from app.config import settings
|
||||
from app.logger import get_logger
|
||||
@@ -46,9 +45,7 @@ _session_stats = {
|
||||
async def get_engine(user_id: str):
|
||||
"""获取或创建用户专属的数据库引擎(线程安全)
|
||||
|
||||
支持PostgreSQL和SQLite两种数据库:
|
||||
- PostgreSQL: 所有用户共享一个数据库,通过user_id字段隔离数据
|
||||
- SQLite: 每个用户一个独立的数据库文件
|
||||
PostgreSQL: 所有用户共享一个数据库,通过user_id字段隔离数据
|
||||
|
||||
Args:
|
||||
user_id: 用户ID
|
||||
@@ -57,7 +54,6 @@ async def get_engine(user_id: str):
|
||||
用户专属的异步引擎
|
||||
"""
|
||||
# PostgreSQL模式:所有用户共享同一个引擎
|
||||
if "postgresql" in settings.database_url:
|
||||
cache_key = "shared_postgres"
|
||||
if cache_key in _engine_cache:
|
||||
return _engine_cache[cache_key]
|
||||
@@ -98,59 +94,6 @@ async def get_engine(user_id: str):
|
||||
|
||||
return _engine_cache[cache_key]
|
||||
|
||||
# SQLite模式:每个用户独立的数据库文件
|
||||
if user_id in _engine_cache:
|
||||
return _engine_cache[user_id]
|
||||
|
||||
async with _cache_lock:
|
||||
if user_id not in _engine_locks:
|
||||
_engine_locks[user_id] = asyncio.Lock()
|
||||
user_lock = _engine_locks[user_id]
|
||||
|
||||
async with user_lock:
|
||||
if user_id not in _engine_cache:
|
||||
db_url = f"sqlite+aiosqlite:///data/ai_story_user_{user_id}.db"
|
||||
engine = create_async_engine(
|
||||
db_url,
|
||||
echo=False,
|
||||
future=True,
|
||||
poolclass=StaticPool,
|
||||
pool_pre_ping=True,
|
||||
pool_recycle=3600,
|
||||
connect_args={
|
||||
"timeout": 30,
|
||||
"check_same_thread": False
|
||||
}
|
||||
)
|
||||
|
||||
try:
|
||||
# 应用优化后的SQLite配置
|
||||
cache_size = -1024 * settings.sqlite_cache_size_mb # 负数表示KB单位
|
||||
mmap_size = settings.sqlite_mmap_size_mb * 1024 * 1024 # 转换为字节
|
||||
|
||||
async with engine.begin() as conn:
|
||||
await conn.execute(text("PRAGMA journal_mode=WAL"))
|
||||
await conn.execute(text("PRAGMA synchronous=NORMAL"))
|
||||
await conn.execute(text(f"PRAGMA cache_size={cache_size}")) # 128MB缓存
|
||||
await conn.execute(text(f"PRAGMA mmap_size={mmap_size}")) # 256MB内存映射
|
||||
await conn.execute(text("PRAGMA temp_store=MEMORY"))
|
||||
await conn.execute(text("PRAGMA busy_timeout=5000"))
|
||||
await conn.execute(text(f"PRAGMA wal_autocheckpoint={settings.sqlite_wal_autocheckpoint}"))
|
||||
|
||||
logger.info(
|
||||
f"✅ 用户 {user_id} 的SQLite数据库已优化\n"
|
||||
f" ├─ WAL模式\n"
|
||||
f" ├─ 缓存: {settings.sqlite_cache_size_mb}MB\n"
|
||||
f" ├─ 内存映射: {settings.sqlite_mmap_size_mb}MB\n"
|
||||
f" └─ 预估并发: 15-20写入用户"
|
||||
)
|
||||
except Exception as e:
|
||||
logger.warning(f"⚠️ 用户 {user_id} SQLite数据库优化失败: {str(e)}")
|
||||
_engine_cache[user_id] = engine
|
||||
logger.info(f"为用户 {user_id} 创建SQLite数据库引擎")
|
||||
|
||||
return _engine_cache[user_id]
|
||||
|
||||
|
||||
async def get_db(request: Request):
|
||||
"""获取数据库会话的依赖函数
|
||||
@@ -411,7 +354,7 @@ async def get_database_stats():
|
||||
"engine_keys": list(_engine_cache.keys()),
|
||||
},
|
||||
"config": {
|
||||
"database_type": "PostgreSQL" if "postgresql" in settings.database_url else "SQLite",
|
||||
"database_type": "PostgreSQL",
|
||||
"pool_size": settings.database_pool_size,
|
||||
"max_overflow": settings.database_max_overflow,
|
||||
"total_connections": settings.database_pool_size + settings.database_max_overflow,
|
||||
@@ -469,19 +412,14 @@ async def check_database_health(user_id: str = None) -> dict:
|
||||
|
||||
try:
|
||||
# 检查引擎是否存在
|
||||
cache_key = "shared_postgres"
|
||||
if user_id:
|
||||
engine = await get_engine(user_id)
|
||||
cache_key = user_id
|
||||
else:
|
||||
if "postgresql" in settings.database_url:
|
||||
cache_key = "shared_postgres"
|
||||
if cache_key not in _engine_cache:
|
||||
result["checks"]["engine"] = {"status": "not_initialized", "healthy": True}
|
||||
return result
|
||||
engine = _engine_cache[cache_key]
|
||||
else:
|
||||
result["checks"]["engine"] = {"status": "skipped", "message": "需要提供user_id检查SQLite"}
|
||||
return result
|
||||
|
||||
# 测试数据库连接
|
||||
AsyncSessionLocal = async_sessionmaker(
|
||||
|
||||
@@ -5,9 +5,8 @@ python-multipart==0.0.20
|
||||
|
||||
# 数据库
|
||||
sqlalchemy==2.0.25
|
||||
aiosqlite==0.19.0 # SQLite支持(保留用于开发环境)
|
||||
asyncpg==0.29.0 # PostgreSQL异步驱动(生产环境)
|
||||
psycopg2-binary==2.9.9 # PostgreSQL同步驱动(备用)
|
||||
asyncpg==0.29.0 # PostgreSQL异步驱动
|
||||
psycopg2-binary==2.9.9 # PostgreSQL同步驱动(用于迁移脚本)
|
||||
|
||||
# 数据验证
|
||||
pydantic==2.12.4
|
||||
|
||||
+60
-45
@@ -3,19 +3,19 @@ services:
|
||||
image: postgres:18-alpine
|
||||
container_name: mumuainovel-postgres
|
||||
environment:
|
||||
POSTGRES_DB: mumuai_novel
|
||||
POSTGRES_USER: mumuai
|
||||
POSTGRES_DB: ${POSTGRES_DB:-mumuai_novel}
|
||||
POSTGRES_USER: ${POSTGRES_USER:-mumuai}
|
||||
POSTGRES_PASSWORD: ${POSTGRES_PASSWORD:-mumuai_password_2024}
|
||||
POSTGRES_INITDB_ARGS: "--encoding=UTF8 --locale=C"
|
||||
TZ: Asia/Shanghai
|
||||
TZ: ${TZ:-Asia/Shanghai}
|
||||
volumes:
|
||||
- postgres_data:/var/lib/postgresql/data
|
||||
- ./backend/scripts/init_postgres.sql:/docker-entrypoint-initdb.d/init.sql:ro
|
||||
ports:
|
||||
- "5432:5432"
|
||||
- "${POSTGRES_PORT:-5432}:5432"
|
||||
restart: unless-stopped
|
||||
healthcheck:
|
||||
test: ["CMD-SHELL", "pg_isready -U mumuai -d mumuai_novel"]
|
||||
test: ["CMD-SHELL", "pg_isready -U ${POSTGRES_USER:-mumuai} -d ${POSTGRES_DB:-mumuai_novel}"]
|
||||
interval: 10s
|
||||
timeout: 5s
|
||||
retries: 5
|
||||
@@ -25,29 +25,29 @@ services:
|
||||
command:
|
||||
- postgres
|
||||
- -c
|
||||
- max_connections=200
|
||||
- max_connections=${POSTGRES_MAX_CONNECTIONS:-200}
|
||||
- -c
|
||||
- shared_buffers=256MB
|
||||
- shared_buffers=${POSTGRES_SHARED_BUFFERS:-256MB}
|
||||
- -c
|
||||
- effective_cache_size=1GB
|
||||
- effective_cache_size=${POSTGRES_EFFECTIVE_CACHE_SIZE:-1GB}
|
||||
- -c
|
||||
- maintenance_work_mem=64MB
|
||||
- maintenance_work_mem=${POSTGRES_MAINTENANCE_WORK_MEM:-64MB}
|
||||
- -c
|
||||
- checkpoint_completion_target=0.9
|
||||
- checkpoint_completion_target=${POSTGRES_CHECKPOINT_COMPLETION_TARGET:-0.9}
|
||||
- -c
|
||||
- wal_buffers=16MB
|
||||
- wal_buffers=${POSTGRES_WAL_BUFFERS:-16MB}
|
||||
- -c
|
||||
- default_statistics_target=100
|
||||
- default_statistics_target=${POSTGRES_DEFAULT_STATISTICS_TARGET:-100}
|
||||
- -c
|
||||
- random_page_cost=1.1
|
||||
- random_page_cost=${POSTGRES_RANDOM_PAGE_COST:-1.1}
|
||||
- -c
|
||||
- effective_io_concurrency=200
|
||||
- effective_io_concurrency=${POSTGRES_EFFECTIVE_IO_CONCURRENCY:-200}
|
||||
- -c
|
||||
- work_mem=4MB
|
||||
- work_mem=${POSTGRES_WORK_MEM:-4MB}
|
||||
- -c
|
||||
- min_wal_size=1GB
|
||||
- min_wal_size=${POSTGRES_MIN_WAL_SIZE:-1GB}
|
||||
- -c
|
||||
- max_wal_size=4GB
|
||||
- max_wal_size=${POSTGRES_MAX_WAL_SIZE:-4GB}
|
||||
|
||||
mumuainovel:
|
||||
build:
|
||||
@@ -59,46 +59,61 @@ services:
|
||||
postgres:
|
||||
condition: service_healthy
|
||||
ports:
|
||||
- "8000:8000"
|
||||
- "${APP_PORT:-8000}:8000"
|
||||
volumes:
|
||||
# 持久化日志
|
||||
- ./logs:/app/logs
|
||||
# 挂载环境变量文件(可选)
|
||||
- ./.env:/app/.env:ro
|
||||
environment:
|
||||
# 应用配置
|
||||
- APP_NAME=AI Story Creator
|
||||
- APP_VERSION=1.0.0
|
||||
- APP_HOST=0.0.0.0
|
||||
- APP_NAME=${APP_NAME:-MuMuAINovel}
|
||||
- APP_VERSION=${APP_VERSION:-1.0.0}
|
||||
- APP_HOST=${APP_HOST:-0.0.0.0}
|
||||
- APP_PORT=8000
|
||||
- DEBUG=false
|
||||
- DEBUG=${DEBUG:-false}
|
||||
|
||||
# 数据库配置(使用PostgreSQL)
|
||||
- DATABASE_URL=postgresql+asyncpg://mumuai:${POSTGRES_PASSWORD:-mumuai_password_2024}@postgres:5432/mumuai_novel
|
||||
# 数据库配置
|
||||
- DATABASE_URL=postgresql+asyncpg://${POSTGRES_USER:-mumuai}:${POSTGRES_PASSWORD:-mumuai_password_2024}@postgres:5432/${POSTGRES_DB:-mumuai_novel}
|
||||
|
||||
# PostgreSQL 连接池配置
|
||||
- DATABASE_POOL_SIZE=30
|
||||
- DATABASE_MAX_OVERFLOW=20
|
||||
- DATABASE_POOL_TIMEOUT=60
|
||||
- DATABASE_POOL_RECYCLE=1800
|
||||
- DATABASE_POOL_PRE_PING=True
|
||||
- DATABASE_POOL_USE_LIFO=True
|
||||
- DATABASE_POOL_SIZE=${DATABASE_POOL_SIZE:-30}
|
||||
- DATABASE_MAX_OVERFLOW=${DATABASE_MAX_OVERFLOW:-20}
|
||||
- DATABASE_POOL_TIMEOUT=${DATABASE_POOL_TIMEOUT:-60}
|
||||
- DATABASE_POOL_RECYCLE=${DATABASE_POOL_RECYCLE:-1800}
|
||||
- DATABASE_POOL_PRE_PING=${DATABASE_POOL_PRE_PING:-True}
|
||||
- DATABASE_POOL_USE_LIFO=${DATABASE_POOL_USE_LIFO:-True}
|
||||
|
||||
- HTTP_PROXY=http://172.16.66.175:7890
|
||||
- HTTPS_PROXY=http://172.16.66.175:7890
|
||||
- NO_PROXY=localhost,127.0.0.1
|
||||
# 代理配置(可选)
|
||||
- HTTP_PROXY=${HTTP_PROXY:-}
|
||||
- HTTPS_PROXY=${HTTPS_PROXY:-}
|
||||
- NO_PROXY=${NO_PROXY:-localhost,127.0.0.1}
|
||||
|
||||
# AI服务配置(建议在 .env 文件中设置)
|
||||
# - OPENAI_API_KEY=${OPENAI_API_KEY}
|
||||
# - GEMINI_API_KEY=${GEMINI_API_KEY}
|
||||
# - ANTHROPIC_API_KEY=${ANTHROPIC_API_KEY}
|
||||
# - DEFAULT_AI_PROVIDER=${DEFAULT_AI_PROVIDER:-gemini}
|
||||
# - DEFAULT_MODEL=${DEFAULT_MODEL:-gemini-2.5-flash}
|
||||
# AI 服务配置
|
||||
- OPENAI_API_KEY=${OPENAI_API_KEY:-}
|
||||
- OPENAI_BASE_URL=${OPENAI_BASE_URL:-https://api.openai.com/v1}
|
||||
- GEMINI_API_KEY=${GEMINI_API_KEY:-}
|
||||
- GEMINI_BASE_URL=${GEMINI_BASE_URL:-}
|
||||
- ANTHROPIC_API_KEY=${ANTHROPIC_API_KEY:-}
|
||||
- ANTHROPIC_BASE_URL=${ANTHROPIC_BASE_URL:-}
|
||||
- DEFAULT_AI_PROVIDER=${DEFAULT_AI_PROVIDER:-openai}
|
||||
- DEFAULT_MODEL=${DEFAULT_MODEL:-gpt-4o-mini}
|
||||
- DEFAULT_TEMPERATURE=${DEFAULT_TEMPERATURE:-0.7}
|
||||
- DEFAULT_MAX_TOKENS=${DEFAULT_MAX_TOKENS:-2000}
|
||||
|
||||
# LinuxDO OAuth配置(⚠️ 必须设置正确的回调地址)
|
||||
# - LINUXDO_CLIENT_ID=${LINUXDO_CLIENT_ID}
|
||||
# - LINUXDO_CLIENT_SECRET=${LINUXDO_CLIENT_SECRET}
|
||||
# - LINUXDO_REDIRECT_URI=${LINUXDO_REDIRECT_URI}
|
||||
# LinuxDO OAuth 配置
|
||||
- LINUXDO_CLIENT_ID=${LINUXDO_CLIENT_ID:-}
|
||||
- LINUXDO_CLIENT_SECRET=${LINUXDO_CLIENT_SECRET:-}
|
||||
- LINUXDO_REDIRECT_URI=${LINUXDO_REDIRECT_URI:-}
|
||||
- FRONTEND_URL=${FRONTEND_URL:-http://localhost:8000}
|
||||
|
||||
# 本地账户登录配置
|
||||
- LOCAL_AUTH_ENABLED=${LOCAL_AUTH_ENABLED:-true}
|
||||
- LOCAL_AUTH_USERNAME=${LOCAL_AUTH_USERNAME:-admin}
|
||||
- LOCAL_AUTH_PASSWORD=${LOCAL_AUTH_PASSWORD:-admin123}
|
||||
- LOCAL_AUTH_DISPLAY_NAME=${LOCAL_AUTH_DISPLAY_NAME:-本地管理员}
|
||||
|
||||
# 会话配置
|
||||
- SESSION_EXPIRE_MINUTES=${SESSION_EXPIRE_MINUTES:-120}
|
||||
- SESSION_REFRESH_THRESHOLD_MINUTES=${SESSION_REFRESH_THRESHOLD_MINUTES:-30}
|
||||
restart: unless-stopped
|
||||
healthcheck:
|
||||
test: ["CMD", "python", "-c", "import urllib.request; urllib.request.urlopen('http://localhost:8000/health')"]
|
||||
|
||||
Reference in New Issue
Block a user