# 数据库架构 **本文引用的文件** - [backend/app/database.py](file://backend/app/database.py) - [backend/app/config.py](file://backend/app/config.py) - [backend/alembic/env.py](file://backend/alembic/env.py) - [backend/alembic/versions/488d0bd5ab01_initial_migration.py](file://backend/alembic/versions/488d0bd5ab01_initial_migration.py) - [backend/requirements.txt](file://backend/requirements.txt) - [backend/app/models/user.py](file://backend/app/models/user.py) - [backend/app/models/query.py](file://backend/app/models/query.py) - [backend/app/models/citation_record.py](file://backend/app/models/citation_record.py) - [backend/app/models/query_task.py](file://backend/app/models/query_task.py) - [backend/app/models/subscription.py](file://backend/app/models/subscription.py) - [backend/app/models/__init__.py](file://backend/app/models/__init__.py) - [backend/app/api/deps.py](file://backend/app/api/deps.py) - [backend/app/api/auth.py](file://backend/app/api/auth.py) - [backend/app/main.py](file://backend/app/main.py) - [docker-compose.yml](file://docker-compose.yml) ## 目录 1. [简介](#简介) 2. [项目结构](#项目结构) 3. [核心组件](#核心组件) 4. [架构总览](#架构总览) 5. [详细组件分析](#详细组件分析) 6. [依赖分析](#依赖分析) 7. [性能考量](#性能考量) 8. [故障排查指南](#故障排查指南) 9. [结论](#结论) 10. [附录](#附录) ## 简介 本文件系统性梳理 GEO 平台的数据库架构,重点覆盖以下方面: - 基于 PostgreSQL 的异步数据库连接配置:SQLAlchemy 异步引擎、连接池与会话生命周期管理 - 连接字符串配置、环境变量管理与安全注意事项 - 异步数据库操作的优势、性能特征与最佳实践 - 连接监控、错误处理与故障恢复机制 - 生产环境配置建议与性能调优指南 ## 项目结构 后端采用 FastAPI + SQLAlchemy 2.x 异步 ORM 架构,数据库层由异步引擎与会话工厂构成,配合 Alembic 进行迁移管理;模型定义位于 models 子包中,并通过 API 层注入依赖进行使用。 ```mermaid graph TB subgraph "后端应用" CFG["配置模块
app/config.py"] DB["数据库引擎与会话
app/database.py"] MODELS["ORM 模型
app/models/*"] ALEMBIC["迁移环境
alembic/env.py"] MIGRATE["初始迁移脚本
alembic/versions/*"] API_DEPS["API 依赖注入
app/api/deps.py"] API_AUTH["认证路由
app/api/auth.py"] MAIN["应用入口与生命周期
app/main.py"] end subgraph "外部服务" PG["PostgreSQL 实例"] REDIS["Redis 实例"] end CFG --> DB DB --> MODELS ALEMBIC --> MIGRATE API_DEPS --> DB API_AUTH --> DB MAIN --> API_AUTH MAIN --> API_DEPS DB --> PG REDIS -. 缓存/任务队列 .-> MAIN ``` 图表来源 - [backend/app/database.py:1-29](file://backend/app/database.py#L1-L29) - [backend/app/config.py:1-17](file://backend/app/config.py#L1-L17) - [backend/alembic/env.py:1-89](file://backend/alembic/env.py#L1-L89) - [backend/alembic/versions/488d0bd5ab01_initial_migration.py:1-128](file://backend/alembic/versions/488d0bd5ab01_initial_migration.py#L1-L128) - [backend/app/api/deps.py:1-43](file://backend/app/api/deps.py#L1-L43) - [backend/app/api/auth.py:1-43](file://backend/app/api/auth.py#L1-L43) - [backend/app/main.py:1-48](file://backend/app/main.py#L1-L48) 章节来源 - [backend/app/database.py:1-29](file://backend/app/database.py#L1-L29) - [backend/app/config.py:1-17](file://backend/app/config.py#L1-L17) - [backend/alembic/env.py:1-89](file://backend/alembic/env.py#L1-L89) - [backend/alembic/versions/488d0bd5ab01_initial_migration.py:1-128](file://backend/alembic/versions/488d0bd5ab01_initial_migration.py#L1-L128) - [backend/app/api/deps.py:1-43](file://backend/app/api/deps.py#L1-L43) - [backend/app/api/auth.py:1-43](file://backend/app/api/auth.py#L1-L43) - [backend/app/main.py:1-48](file://backend/app/main.py#L1-L48) ## 核心组件 - 异步引擎与会话工厂 - 使用 SQLAlchemy 异步引擎创建数据库连接,关闭 echo,启用 future 模式 - 会话工厂配置为非自动提交、非自动刷新、关闭提交时过期,确保事务边界清晰 - 提供异步上下文管理的会话生成器,保证在请求结束时正确关闭会话 - 配置与连接字符串 - 通过 Pydantic Settings 从 .env 文件加载配置,包含 DATABASE_URL、REDIS_URL、JWT_SECRET 等 - 默认 DATABASE_URL 指向本地或容器内 PostgreSQL 实例 - 模型与索引 - 用户、查询、引用记录、查询任务、订阅等核心实体,均采用 PostgreSQL UUID 主键与 JSONB 字段 - 在高频查询字段上建立复合索引,提升读取性能 - 迁移与初始化 - Alembic 环境支持离线与在线迁移,使用异步引擎执行迁移 - 初始迁移脚本创建表结构与索引,定义外键约束与默认值 章节来源 - [backend/app/database.py:1-29](file://backend/app/database.py#L1-L29) - [backend/app/config.py:1-17](file://backend/app/config.py#L1-L17) - [backend/app/models/user.py:1-41](file://backend/app/models/user.py#L1-L41) - [backend/app/models/query.py:1-55](file://backend/app/models/query.py#L1-L55) - [backend/app/models/citation_record.py:1-42](file://backend/app/models/citation_record.py#L1-L42) - [backend/app/models/query_task.py:1-39](file://backend/app/models/query_task.py#L1-L39) - [backend/app/models/subscription.py:1-37](file://backend/app/models/subscription.py#L1-L37) - [backend/alembic/env.py:64-88](file://backend/alembic/env.py#L64-L88) - [backend/alembic/versions/488d0bd5ab01_initial_migration.py:21-128](file://backend/alembic/versions/488d0bd5ab01_initial_migration.py#L21-L128) ## 架构总览 下图展示异步数据库连接在应用中的整体流转:FastAPI 路由通过依赖注入获取 AsyncSession,执行数据库操作后自动释放;迁移通过 Alembic 异步引擎执行;配置从 .env 加载 DATABASE_URL。 ```mermaid sequenceDiagram participant Client as "客户端" participant API as "FastAPI 路由" participant Deps as "依赖注入(get_db)" participant Session as "AsyncSession" participant Engine as "异步引擎" participant PG as "PostgreSQL" Client->>API : "HTTP 请求" API->>Deps : "解析依赖(获取会话)" Deps->>Session : "创建/获取会话" Session->>Engine : "执行 SQL" Engine->>PG : "发送查询" PG-->>Engine : "返回结果" Engine-->>Session : "映射为模型" Session-->>API : "业务结果" API-->>Client : "响应" API->>Deps : "请求结束" Deps->>Session : "关闭会话" ``` 图表来源 - [backend/app/api/auth.py:13-42](file://backend/app/api/auth.py#L13-L42) - [backend/app/api/deps.py:16-42](file://backend/app/api/deps.py#L16-L42) - [backend/app/database.py:23-28](file://backend/app/database.py#L23-L28) ## 详细组件分析 ### 异步引擎与会话生命周期 - 引擎创建 - 使用异步引擎,echo 关闭,future 启用,避免冗余日志与兼容性问题 - 会话工厂 - 非自动提交、非自动刷新、关闭提交时过期,便于显式控制事务 - 会话生成器 - 通过上下文管理器确保异常时也能正确关闭会话,避免连接泄漏 ```mermaid flowchart TD Start(["进入 get_db"]) --> NewSession["创建 AsyncSessionLocal()"] NewSession --> TryBlock["进入 try 块并 yield 会话"] TryBlock --> FinallyBlock["finally 块中关闭会话"] FinallyBlock --> End(["退出 get_db"]) ``` 图表来源 - [backend/app/database.py:23-28](file://backend/app/database.py#L23-L28) 章节来源 - [backend/app/database.py:1-29](file://backend/app/database.py#L1-L29) ### 连接字符串与环境变量管理 - 连接字符串 - 默认 DATABASE_URL 指向 PostgreSQL 实例,可在 .env 中覆盖 - 环境变量加载 - 通过 Pydantic SettingsConfigDict 从 .env 加载,忽略未知字段 - 安全注意事项 - 生产环境务必使用强密钥与加密传输 - 不要在代码中硬编码敏感信息,优先使用环境变量与密钥管理服务 章节来源 - [backend/app/config.py:4-16](file://backend/app/config.py#L4-L16) ### 数据模型与索引策略 - 用户模型 - UUID 主键、邮箱唯一、密码哈希、计划与配额字段 - 查询模型 - 外键关联用户、JSONB 存储平台与别名、多字段索引优化 - 引用记录模型 - JSONB 存储竞品品牌与原始响应,按查询与时间、平台建立索引 - 查询任务模型 - 状态字段索引,便于任务调度与状态统计 - 订阅模型 - 金额与支付信息存储,日期范围与状态管理 ```mermaid erDiagram USERS { uuid id PK string email UK string password_hash string name string plan int max_queries bool is_active timestamptz created_at timestamptz updated_at } QUERIES { uuid id PK uuid user_id FK string keyword string target_brand jsonb brand_aliases jsonb platforms string frequency string status timestamptz last_queried_at timestamptz next_query_at timestamptz created_at timestamptz updated_at } CITATION_RECORDS { uuid id PK uuid query_id FK string platform bool cited int citation_position text citation_text jsonb competitor_brands text raw_response timestamptz queried_at } QUERY_TASKS { uuid id PK uuid query_id FK string platform string status text error_message timestamptz scheduled_at timestamptz started_at timestamptz completed_at } SUBSCRIPTIONS { uuid id PK uuid user_id FK string plan string status date start_date date end_date numeric amount string payment_method string payment_id timestamptz created_at } USERS ||--o{ QUERIES : "拥有" QUERIES ||--o{ CITATION_RECORDS : "产生" QUERIES ||--o{ QUERY_TASKS : "驱动" USERS ||--o{ SUBSCRIPTIONS : "订阅" ``` 图表来源 - [backend/app/models/user.py:11-41](file://backend/app/models/user.py#L11-L41) - [backend/app/models/query.py:11-55](file://backend/app/models/query.py#L11-L55) - [backend/app/models/citation_record.py:11-42](file://backend/app/models/citation_record.py#L11-L42) - [backend/app/models/query_task.py:11-39](file://backend/app/models/query_task.py#L11-L39) - [backend/app/models/subscription.py:11-37](file://backend/app/models/subscription.py#L11-L37) 章节来源 - [backend/app/models/user.py:1-41](file://backend/app/models/user.py#L1-L41) - [backend/app/models/query.py:1-55](file://backend/app/models/query.py#L1-L55) - [backend/app/models/citation_record.py:1-42](file://backend/app/models/citation_record.py#L1-L42) - [backend/app/models/query_task.py:1-39](file://backend/app/models/query_task.py#L1-L39) - [backend/app/models/subscription.py:1-37](file://backend/app/models/subscription.py#L1-L37) ### 迁移与初始化 - 离线/在线迁移 - 离线模式直接使用 DATABASE_URL;在线模式通过异步引擎建立连接并执行迁移 - 使用 NullPool 避免额外连接池开销 - 初始迁移 - 创建 users、queries、citation_records、query_tasks、subscriptions 表 - 添加必要的外键与索引,确保查询性能与数据一致性 ```mermaid sequenceDiagram participant CLI as "Alembic CLI" participant Env as "env.py" participant Engine as "异步引擎" participant Conn as "连接" participant DB as "PostgreSQL" CLI->>Env : "run_migrations_online()" Env->>Engine : "create_async_engine(DATABASE_URL, poolclass=NullPool)" Engine->>Conn : "connect()" Conn->>DB : "执行迁移" DB-->>Conn : "返回迁移结果" Conn-->>Engine : "完成迁移" Engine-->>Env : "dispose()" ``` 图表来源 - [backend/alembic/env.py:64-88](file://backend/alembic/env.py#L64-L88) - [backend/alembic/versions/488d0bd5ab01_initial_migration.py:21-128](file://backend/alembic/versions/488d0bd5ab01_initial_migration.py#L21-L128) 章节来源 - [backend/alembic/env.py:1-89](file://backend/alembic/env.py#L1-L89) - [backend/alembic/versions/488d0bd5ab01_initial_migration.py:1-128](file://backend/alembic/versions/488d0bd5ab01_initial_migration.py#L1-L128) ### API 依赖注入与会话使用 - 依赖注入 - OAuth2 密钥流用于令牌校验;通过 get_db 获取 AsyncSession - 典型流程 - 注册/登录接口使用 AsyncSession 执行写入与查询 - 当前用户接口通过令牌解析与数据库查询返回用户信息 ```mermaid sequenceDiagram participant Client as "客户端" participant Auth as "认证路由" participant Deps as "get_current_user" participant DB as "AsyncSession" participant Model as "User 模型" Client->>Auth : "POST /api/v1/auth/login" Auth->>DB : "执行认证查询" DB-->>Auth : "返回用户对象" Auth-->>Client : "返回访问令牌与用户信息" Client->>Auth : "GET /api/v1/auth/me" Auth->>Deps : "校验令牌并解析用户ID" Deps->>DB : "查询用户" DB-->>Deps : "返回用户" Deps-->>Client : "返回当前用户" ``` 图表来源 - [backend/app/api/auth.py:13-42](file://backend/app/api/auth.py#L13-L42) - [backend/app/api/deps.py:16-42](file://backend/app/api/deps.py#L16-L42) 章节来源 - [backend/app/api/auth.py:1-43](file://backend/app/api/auth.py#L1-L43) - [backend/app/api/deps.py:1-43](file://backend/app/api/deps.py#L1-L43) ## 依赖分析 - 组件耦合 - API 层通过依赖注入使用数据库会话,降低耦合度 - 模型与数据库层解耦,仅依赖 Base 与类型注解 - 外部依赖 - SQLAlchemy 2.x 异步 ORM、asyncpg、Alembic - FastAPI、Pydantic Settings、Redis(缓存/任务) ```mermaid graph LR API_AUTH["app/api/auth.py"] --> DEPS["app/api/deps.py"] DEPS --> DB["app/database.py"] API_AUTH --> DB DB --> CONFIG["app/config.py"] DB --> MODELS["app/models/*"] ALEMBIC_ENV["alembic/env.py"] --> CONFIG ALEMBIC_ENV --> MODELS ALEMBIC_MIG["alembic/versions/*"] --> MODELS ``` 图表来源 - [backend/app/api/auth.py:1-43](file://backend/app/api/auth.py#L1-L43) - [backend/app/api/deps.py:1-43](file://backend/app/api/deps.py#L1-L43) - [backend/app/database.py:1-29](file://backend/app/database.py#L1-L29) - [backend/app/config.py:1-17](file://backend/app/config.py#L1-L17) - [backend/alembic/env.py:1-89](file://backend/alembic/env.py#L1-L89) - [backend/alembic/versions/488d0bd5ab01_initial_migration.py:1-128](file://backend/alembic/versions/488d0bd5ab01_initial_migration.py#L1-L128) 章节来源 - [backend/requirements.txt:1-35](file://backend/requirements.txt#L1-L35) ## 性能考量 - 异步优势 - 高并发场景下减少阻塞,提升吞吐量 - 与 FastAPI 协同,充分利用事件循环 - 连接池与会话 - 默认未显式配置连接池参数,建议在生产中根据 QPS 与实例规格调整最大连接数、空闲连接数与超时 - 索引与查询 - 已在高频查询字段建立索引,避免全表扫描 - 对 JSONB 字段的查询建议结合 GIN 索引(如需) - 写入优化 - 批量写入与事务合并可显著降低写入延迟 - 监控与观测 - 建议集成数据库性能视图与慢查询日志 - 结合应用指标(请求耗时、错误率)定位瓶颈 ## 故障排查指南 - 连接失败 - 检查 DATABASE_URL 是否正确,网络连通性与防火墙 - 确认 PostgreSQL 实例健康状态与认证凭据 - 迁移失败 - 离线/在线模式分别检查配置与权限 - 查看 Alembic 输出与 PostgreSQL 日志 - 会话泄漏 - 确保所有分支均能到达 finally 块,避免异常中断导致会话未关闭 - 错误处理 - API 层对认证失败与数据库异常进行标准化响应 - 建议增加重试与熔断策略(如适用) 章节来源 - [backend/app/database.py:23-28](file://backend/app/database.py#L23-L28) - [backend/alembic/env.py:64-88](file://backend/alembic/env.py#L64-L88) - [backend/app/api/auth.py:13-42](file://backend/app/api/auth.py#L13-L42) - [backend/app/api/deps.py:16-42](file://backend/app/api/deps.py#L16-L42) ## 结论 GEO 项目采用 SQLAlchemy 异步 ORM 与 FastAPI 构建了高并发、可维护的数据库层。通过合理的模型设计、索引策略与依赖注入,实现了清晰的职责分离与良好的扩展性。建议在生产环境中完善连接池参数、监控体系与安全策略,持续优化查询与写入路径。 ## 附录 ### 生产环境配置建议 - 连接字符串与环境变量 - 使用独立 .env 文件管理 DATABASE_URL,避免硬编码 - 在容器编排中通过环境注入,确保不同环境隔离 - 连接池与会话 - 显式配置最大连接数、空闲连接数、连接超时与回收策略 - 控制会话生命周期,避免长事务与长时间持有连接 - 安全 - 使用强口令与 TLS 加密传输 - 限制数据库用户权限,最小化授权 - 监控与可观测性 - 集成数据库性能视图与慢查询日志 - 应用层记录关键指标(QPS、P95/P99、错误率) - 备份与恢复 - 定期备份策略与演练,确保可快速恢复 ### 性能调优清单 - 索引优化 - 对高频过滤与排序字段建立合适索引 - 对 JSONB 字段查询考虑 GIN 索引 - 查询优化 - 减少 N+1 查询,使用 select_in_load 或 joinedload - 合理分页与投影,避免 SELECT * - 写入优化 - 批量插入与事务合并 - 写入热点拆分与读写分离(如需要) - 连接与资源 - 合理设置连接池大小,避免过度占用 - 及时关闭会话与释放资源