startup-plan/技术设计/api-server/[进行中]-架构总览.md
2026-05-15 17:29:57 +08:00

1186 lines
26 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

---
source: startup-plan/个人开发者创业 v0.1 + 完全版 + AI回答.md 架构深化方案
updated: 2026-05-09
---
# 知习 api-server 后端架构规划
> 「知习」是一款 AI-first 的系统化学习 App。后端需要同时服务 iOS App 和 Web 官网。
> 核心功能包括知识库、主动回忆、AI 学习分析、间隔复习、待巩固项、学习活跃记录、消息通知和反馈。
---
## 1. 架构总览:模块化单体 + Redis + Worker
**不要微服务。** 当前最适合的是:
> **模块化单体架构 Monolithic Modular Architecture**
>
> 一个后端项目,内部按业务模块拆清楚。
```text
iOS App
Web 官网
统一 API 后端NestJS 模块化单体)
数据库 / Redis / 文件存储 / AI 服务
Worker 异步任务
```
---
## 2. 最终技术栈
```text
后端框架NestJS + TypeScript
ORMPrisma
数据库PostgreSQL推荐MySQL 亦可
缓存/队列Redis
队列系统BullMQ
接口文档Swagger / OpenAPI
文件存储:本地开发先本地存,后期接对象存储
AIProvider 抽象 + 一个真实模型 + MockProvider
部署Docker Compose
反向代理Nginx
域名api.longde.cloud
```
Docker Compose 项目服务规划:
```text
api-server — NestJS 后端
postgres — 主数据库
redis — 缓存 + 队列
worker — 异步任务处理
nginx — 反向代理 + HTTPS
```
---
## 3. 为什么选这个技术栈
### NestJS
项目会越来越模块化。NestJS 的模块结构适合长期维护:
```text
用户 / 知识库 / 学习记录 / AI 分析 / 复习计划 / 待巩固项 / 通知 / 反馈 / 订阅
```
Express 也能做,但后期容易自己手写一堆规范,最后变乱。
### Prisma
- 类型安全的 ORM自动生成 TypeScript 类型
- 迁移管理清晰
- 与 NestJS 集成良好
- AI Agent 按 schema 生成代码能力好
### PostgreSQL优于 MySQL
- 更适合 JSON 数据AI 分析结果)
- 支持全文检索
- 后续可扩展 pgvector 做向量检索
- 如果更熟悉 MySQL也可以先用 MySQL
### Redis + BullMQ
Redis 不只是缓存,在知习系统里做四件事:
```text
缓存 → 短期数据加速
队列 → AI 分析 / 资料导入 / 通知任务
限流 → AI 调用频控 / 用户请求限流
临时状态 → 任务处理中状态 / 防重复提交锁
```
---
## 4. 前后端职责分离
| 端 | 职责 |
|---|------|
| iOS 客户端 | 页面展示、用户交互、本地状态、登录入口、学习流程体验 |
| 后端 API | 用户身份、AI API 代理、学习记录、AI 分析、学习画像、复习计划、待巩固项、通知、反馈 |
| Worker | AI 分析任务异步处理、资料导入异步处理、通知分发 |
| AI 模型 | 分析用户输入、生成学习反馈、识别薄弱点、生成复习建议、辅助学习对话 |
| 官网 | 产品介绍、SEO、隐私政策、用户协议、支持页面、等待名单 |
---
## 5. 数据库和 Redis 的分工
```
PostgreSQL / MySQL长期真实数据
Redis短期状态、缓存、队列、限流
文件存储PDF、图片、附件
AI 服务:分析、总结、生成复习题
```
一句话:
> **数据库存事实Redis 管状态。**
### Redis 适合做
- AI 分析任务队列
- 资料导入任务队列
- 通知任务队列
- 用户请求限流
- AI 调用次数计数
- 任务处理中状态
- 防重复提交锁
- 短期缓存
### Redis 不适合做主数据
这些必须进数据库:
- 用户资料
- 知识库
- 学习记录
- AI 分析结果
- 待巩固项
- 复习计划
- 学习活跃记录
- 通知记录
---
## 6. 后端目录结构
```text
api-server/
├── src/
│ ├── main.ts
│ ├── app.module.ts
│ │
│ ├── config/
│ │ ├── app.config.ts
│ │ ├── database.config.ts
│ │ ├── redis.config.ts
│ │ ├── jwt.config.ts
│ │ ├── ai.config.ts
│ │ └── storage.config.ts
│ │
│ ├── common/
│ │ ├── constants/
│ │ ├── decorators/
│ │ ├── guards/
│ │ ├── interceptors/
│ │ ├── filters/
│ │ ├── pipes/
│ │ ├── dto/
│ │ ├── types/
│ │ └── utils/
│ │
│ ├── infrastructure/
│ │ ├── database/
│ │ ├── redis/
│ │ ├── queue/
│ │ ├── ai/
│ │ │ ├── prompts/
│ │ │ └── providers/
│ │ ├── storage/
│ │ └── logger/
│ │
│ ├── modules/
│ │ ├── auth/
│ │ ├── users/
│ │ ├── knowledge-base/
│ │ ├── knowledge-items/
│ │ ├── document-import/
│ │ ├── learning-session/
│ │ ├── active-recall/
│ │ ├── ai-analysis/
│ │ ├── review/
│ │ ├── focus-items/
│ │ ├── learning-activity/
│ │ ├── notifications/
│ │ ├── feedback/
│ │ └── system/
│ │
│ └── workers/
│ ├── ai-analysis.worker.ts
│ ├── document-import.worker.ts
│ └── notification.worker.ts
├── prisma/
│ ├── schema.prisma
│ └── migrations/
├── docker-compose.yml
├── Dockerfile
├── .env.example
└── package.json
```
---
## 7. 各模块职责
### 7.1 Auth 模块
负责 Apple 登录、JWT、刷新 Token、退出登录、账号注销。
App Store 上架要求 Sign in with Apple这是必须做的。
### 7.2 Users 模块
负责用户资料、头像、昵称、学习身份、学习方向、学习偏好。
### 7.3 Knowledge Base 模块
负责知识库创建、列表、详情、编辑、删除、标签。
### 7.4 Knowledge Items 模块
负责具体知识点、章节、内容段落、关键概念、标签、关联关系。
### 7.5 Document Import 模块
负责上传文件、粘贴文本、链接导入、导入状态、解析进度、导入成功/失败。
这里非常适合用 Redis Queue 做异步处理。
### 7.6 Learning Session 模块
负责一次学习过程:开始学习、结束学习、学习时长、学习内容、学习模式、完成状态。
这是学习活跃图的数据来源之一。
### 7.7 Active Recall 模块
负责主动回忆:回忆问题、用户回答、语音回答、回答提交、回答历史。
### 7.8 AI Analysis 模块
负责提交分析任务、分析状态、AI 分析结果、掌握度、薄弱点、改进建议、下一步建议。
**必须走 Redis Queue 异步处理。**
### 7.9 Focus Items 模块
「待巩固项」——类似 GitHub Issue但在知习里叫待巩固项。
负责AI 自动生成待巩固项、用户手动添加、状态(待处理/已加入复习/已完成)、关联知识点、关联学习记录。
### 7.10 Review 模块
负责复习卡片、到期复习、间隔复习计划、复习结果、掌握程度选择、下次复习时间。
### 7.11 Learning Activity 模块
负责学习活跃图每日学习时长、主动回忆次数、复习次数、AI 分析次数、完成学习闭环次数、学习活跃度等级。
活跃图数据最终写入数据库Redis 可做临时累计。
### 7.12 Notifications 模块
负责复习提醒、AI 分析完成提醒、学习建议、系统通知、已读/未读。
### 7.13 Feedback 模块
负责 Web 和 App 反馈:用户反馈、问题类型、邮箱、设备、处理状态。
### 7.14 System 模块
健康检查、应用状态、基础运维接口。
---
## 8. 模块优先级
### v0.1 必须实现
```text
auth
users
knowledge-base
knowledge-items
learning-session
active-recall
ai-analysis
focus-items
review
learning-activity
feedback
system
```
### v0.1 暂缓
```text
document-import — 先手动录入内容
notifications — 先不做推送
billing — 暂无付费
subscription — 暂无订阅
admin-dashboard — 暂无管理后台
team — 单人使用
```
---
## 9. API 路由规划
```text
GET /api/health
POST /api/auth/apple
POST /api/auth/refresh
POST /api/auth/logout
GET /api/users/me
PATCH /api/users/me
PATCH /api/users/me/preferences
GET /api/knowledge-bases
POST /api/knowledge-bases
GET /api/knowledge-bases/:id
PATCH /api/knowledge-bases/:id
DELETE /api/knowledge-bases/:id
GET /api/knowledge-bases/:id/items
GET /api/knowledge-items/:id
POST /api/knowledge-items
POST /api/imports
GET /api/imports/:id/status
POST /api/learning-sessions
POST /api/learning-sessions/:id/end
GET /api/active-recalls
POST /api/active-recalls/:id/submit
POST /api/ai-analysis
GET /api/ai-analysis/:id
GET /api/ai-analysis/jobs/:jobId/status
GET /api/focus-items
POST /api/focus-items
PATCH /api/focus-items/:id
POST /api/focus-items/:id/complete
GET /api/reviews/due
POST /api/reviews/:id/submit
GET /api/activity/heatmap
GET /api/activity/summary
GET /api/notifications
POST /api/notifications/:id/read
POST /api/feedback
```
---
## 10. 关键请求流程
核心异步流程详见 [23. 异步模块额外文件 - AI 分析模块完整流程](#23-异步模块额外文件queue--processor)。
---
## 11. 核心 AI 接口
### POST /api/ai-analysis提交异步任务
输入:
```json
{
"sessionId": "session_001",
"lessonId": "lesson_001",
"userInput": "用户写下的答案或笔记",
"context": {
"lessonTitle": "材料阅读方法",
"objectives": ["理解材料结构", "提取关键要点"],
"keyPoints": ["问题", "原因", "影响", "对策"]
}
}
```
返回:
```json
{
"jobId": "job_abc123",
"status": "pending"
}
```
### GET /api/ai-analysis/jobs/:jobId/status查询状态
```json
{
"jobId": "job_abc123",
"status": "completed",
"result": {
"masteryScore": 3,
"understandingLevel": "基本理解",
"summary": "用户能理解主要内容,但要点不完整。",
"strengths": ["表达清楚"],
"weakPoints": ["遗漏关键要点", "逻辑层次不足"],
"suggestions": ["补充第二个要点", "先概括再展开"],
"reviewNeeded": true,
"nextAction": "明天重新回答本节主动回忆问题。"
}
}
```
---
## 12. AI Provider 层设计
```text
AIService
├── MiniMaxProvider
├── DeepSeekProvider
├── OpenAIProvider
└── MockProvider
```
### MockProvider
v0.1 强烈建议做 MockProvider
- 没有 API Key 时也能开发
- AI 服务出问题时能测试流程
- 降低开发成本
- 方便录 Demo
### 候选模型
MiniMax / DeepSeek / 通义千问 / OpenAI / Claude / Gemini
### 模型选择原则
1. 中文能力好
2. 成本可控
3. API 稳定
4. 支持结构化输出
5. 速度可以接受
6. 容易接入
7. 可替换
---
## 13. 核心实体/数据模型
```text
User
├── id
├── appleUserId
├── displayName
├── email
├── preferredLanguage
├── learningDirection
├── createdAt
├── lastLoginAt
└── status
KnowledgeBase
├── id
├── userId
├── title
├── description
├── language
├── tags
├── createdAt
└── updatedAt
KnowledgeItem
├── id
├── knowledgeBaseId
├── parentId
├── title
├── content
├── type (chapter/section/concept)
├── objectives
├── keyPoints
├── recallQuestions
├── order
└── estimatedMinutes
DocumentImport
├── id
├── userId
├── knowledgeBaseId
├── sourceType (file/text/link)
├── status (pending/processing/completed/failed)
├── result
├── createdAt
└── completedAt
LearningSession
├── id
├── userId
├── knowledgeItemId
├── startedAt
├── endedAt
├── durationSeconds
├── mode (reading/recall/review)
└── completedAt
ActiveRecall
├── id
├── sessionId
├── question
├── userAnswer
├── answerType (text/voice)
├── submittedAt
AIAnalysis
├── id
├── jobId
├── userId
├── sessionId
├── inputText
├── outputJson
├── masteryScore
├── weakPoints
├── suggestions
├── modelName
├── costEstimate
├── status (pending/processing/completed/failed)
├── createdAt
└── completedAt
FocusItem
├── id
├── userId
├── knowledgeItemId
├── aiAnalysisId
├── title
├── description
├── status (pending/in_review/completed)
├── createdAt
└── completedAt
ReviewTask
├── id
├── userId
├── knowledgeItemId
├── focusItemId
├── reviewType
├── scheduledAt
├── completedAt
├── masteryChoice
├── nextReviewAt
└── status
LearningActivity
├── id
├── userId
├── date
├── durationSeconds
├── recallCount
├── reviewCount
├── analysisCount
├── closedLoopCount
├── activityLevel
└── updatedAt
Notification
├── id
├── userId
├── type
├── title
├── body
├── data (JSON)
├── isRead
└── createdAt
Feedback
├── id
├── userId
├── type
├── content
├── email
├── device
├── status
└── createdAt
```
---
## 14. 掌握度评分0-5分
```text
0 = 没有作答 / 无法判断
1 = 基本没理解
2 = 理解较弱
3 = 基本理解
4 = 理解较好
5 = 掌握很好
```
这不是考试分数,是产品内部用于安排复习和学习建议的参考值。
---
## 15. 账号体系
### 第一版登录方式
```text
Sign in with Apple
```
暂不做微信登录、手机号登录、邮箱密码登录、Google 登录。
### 账号边界
第一版账号只解决:登录、识别用户、保存学习记录、保存 AI 分析结果、保存基础偏好。
暂不做:好友系统、用户主页、头像上传、多登录方式绑定、复杂权限系统。
---
## 16. 部署方案
### 当前服务器
- IP: 81.70.187.179
- 配置: 4 核 4G40G SSD
- 当前运行: Gitea端口 3000+ Nginx
- SSH: ubuntu 用户 + WangDL.pem 密钥
### 推荐部署方式
```text
Nginx — 反向代理,已有
api-server (NestJS) — 端口 3001
postgres / mysql — 端口 5432 / 3306
redis — 端口 6379
worker (BullMQ) — 同代码仓库,独立进程
gitea — 端口 3000继续保留
```
建议新增 Nginx 配置 `api.longde.cloud` → 反向代理到 NestJS 端口。
### 资源评估
Gitea 当前资源占用很低(内存 ~500MB剩余 ~3GB 内存、33GB 磁盘足够跑 api-server + PostgreSQL + Redis。
---
## 17. 域名与 Nginx 规划
```text
longde.cloud 官网首页
api.longde.cloud 后端 API需新增 Nginx 配置)
git.longde.cloud Gitea 代码仓库(已有)
```
### 待新增 Nginx 配置api.longde.cloud
```nginx
server {
server_name api.longde.cloud;
location / {
proxy_pass http://127.0.0.1:3001;
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;
}
listen 443 ssl;
ssl_certificate /etc/letsencrypt/live/api.longde.cloud/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/api.longde.cloud/privkey.pem;
}
```
---
## 18. 技术里程碑
### 里程碑 1最小后端
- NestJS 项目初始化
- Prisma schema 定义
- PostgreSQL/MySQL 连接
- 用户表、知识库表
- AI MockProvider
- Swagger 文档
### 里程碑 2真实 AI 接入
- Redis + BullMQ 接入
- AI Provider 抽象
- 接入一个真实模型
- AI 分析异步流程
- Worker 处理 AI 任务
### 里程碑 3TestFlight 前准备
- Sign in with Apple
- 后端用户身份记录
- 基础错误处理
- Docker Compose 一键部署
- Nginx 反向代理配置
---
## 19. 商业化与支付(未来)
### 支付流程
```text
用户在 iOS App 内付款 → Apple IAP 完成交易 → 后端记录用户权益 → 用户获得权益
```
### 核心
不要让 Apple IAP 成为整个商业系统。真正核心的是:
```text
用户系统 + 订单系统 + 权益系统
```
### 当前暂缓
Apple IAP / 月订阅 / 年订阅 / 免费试用 / 订阅权益系统 / AI 成本精算
---
## 20. 当前技术不做清单
- 微服务 / Kubernetes / 多云部署
- 完整后台管理系统 / CMS
- 完整 RAG / 向量数据库(第一版)
- 多模型自动路由
- AI Agent 工具调用系统
- 支付系统
- 复杂数据分析平台
- Android / Web 学习端
---
## 21. 四层代码分层原则
整体分四层,每一层有明确的职责边界:
```text
Controller 层:接收请求,处理参数,返回响应
Service 层:业务逻辑
Repository 层:数据库读写
Infrastructure 层Redis、Queue、AI、Storage 等基础设施
```
简单理解:
```text
Controller 不写业务
Service 不直接写复杂 SQL
Repository 不写业务判断
Infrastructure 不知道具体业务,只提供能力
```
一句话纪律:
```text
Controller = 接口 Service = 业务 Repository = 数据库
Infrastructure = 外部能力 Queue/Processor = 异步任务 DTO = 请求/响应结构
```
第一版不要追求所有业务一次写完,但**架构模板必须先统一**。
---
## 22. 模块内部统一模板
每个业务模块都按这个结构来。以 `knowledge-base` 为例:
```text
modules/knowledge-base/
├── knowledge-base.module.ts
├── knowledge-base.controller.ts
├── knowledge-base.service.ts
├── knowledge-base.repository.ts
├── dto/
│ ├── create-knowledge-base.dto.ts
│ ├── update-knowledge-base.dto.ts
│ ├── query-knowledge-base.dto.ts
│ └── knowledge-base-response.dto.ts
├── types/
│ └── knowledge-base.types.ts
└── constants/
└── knowledge-base.constants.ts
```
### 22.1 xxx.module.ts
```text
作用:
- 注册 controller
- 注册 service
- 注册 repository
- 引入依赖模块
- 导出给其他模块使用
```
```ts
@Module({
controllers: [KnowledgeBaseController],
providers: [KnowledgeBaseService, KnowledgeBaseRepository],
exports: [KnowledgeBaseService],
})
export class KnowledgeBaseModule {}
```
### 22.2 xxx.controller.ts
**只做这些事:**
1. 定义路由
2. 接收参数
3. 调用 service
4. 返回结果
**不要在 Controller 里写业务判断。**
```ts
@Controller('knowledge-bases')
export class KnowledgeBaseController {
constructor(private readonly service: KnowledgeBaseService) {}
@Post()
create(@Body() dto: CreateKnowledgeBaseDto, @CurrentUser() user: UserPayload) {
return this.service.create(user.id, dto);
}
@Get()
findAll(@CurrentUser() user: UserPayload, @Query() query: QueryKnowledgeBaseDto) {
return this.service.findAll(user.id, query);
}
@Get(':id')
findOne(@Param('id') id: string, @CurrentUser() user: UserPayload) {
return this.service.findOne(user.id, id);
}
}
```
### 22.3 xxx.service.ts
**这里写:**
1. 权限判断
2. 业务规则
3. 调用 repository
4. 调用其他模块 service
5. 调用 queue / AI / Redis
6. 组织返回结果
```ts
@Injectable()
export class KnowledgeBaseService {
constructor(
private readonly repository: KnowledgeBaseRepository,
) {}
async create(userId: string, dto: CreateKnowledgeBaseDto) {
const count = await this.repository.countByUserId(userId);
if (count >= MAX_KNOWLEDGE_BASE_COUNT) {
throw new BadRequestException('知识库数量已达到上限');
}
return this.repository.create(userId, dto);
}
async findOne(userId: string, id: string) {
const knowledgeBase = await this.repository.findById(id);
if (!knowledgeBase || knowledgeBase.userId !== userId) {
throw new NotFoundException('知识库不存在');
}
return knowledgeBase;
}
}
```
### 22.4 xxx.repository.ts
**只写数据库操作,不写复杂业务。**
```ts
@Injectable()
export class KnowledgeBaseRepository {
constructor(private readonly prisma: PrismaService) {}
create(userId: string, dto: CreateKnowledgeBaseDto) {
return this.prisma.knowledgeBase.create({
data: { userId, name: dto.name, description: dto.description },
});
}
findById(id: string) {
return this.prisma.knowledgeBase.findUnique({ where: { id } });
}
countByUserId(userId: string) {
return this.prisma.knowledgeBase.count({ where: { userId } });
}
}
```
### 22.5 dto/
DTO 就是接口输入输出的数据结构。
用途:
1. 校验请求参数
2. 生成 Swagger 文档
3. 让接口结构清楚
```ts
export class CreateKnowledgeBaseDto {
@ApiProperty({ example: '认知心理学' })
@IsString()
@IsNotEmpty()
name: string;
@ApiProperty({ example: '系统学习认知心理学基础概念', required: false })
@IsOptional()
@IsString()
description?: string;
}
```
### 22.6 types/
放模块内部类型。如果是数据库模型,不放这里,放 Prisma。
```ts
export type KnowledgeBaseStatus = 'active' | 'archived';
export interface KnowledgeBaseStats {
itemCount: number;
completedCount: number;
reviewDueCount: number;
}
```
### 22.7 constants/
放模块常量。
```ts
export const MAX_KNOWLEDGE_BASE_COUNT = 20;
export const DEFAULT_KNOWLEDGE_BASE_COVER = 'default-blue';
```
---
## 23. 异步模块额外文件Queue + Processor
涉及异步任务的模块,需要在标准模板上加 `queue``processor``jobs`
`ai-analysis` 为例:
```text
modules/ai-analysis/
├── ai-analysis.module.ts
├── ai-analysis.controller.ts
├── ai-analysis.service.ts
├── ai-analysis.repository.ts
├── ai-analysis.queue.ts ← 封装 BullMQ 队列
├── ai-analysis.processor.ts ← 消费任务,调用大模型
├── dto/
│ ├── create-ai-analysis.dto.ts
│ ├── query-ai-analysis.dto.ts
│ └── ai-analysis-response.dto.ts
├── jobs/
│ └── ai-analysis.job.ts ← 队列任务数据结构
├── types/
│ └── ai-analysis.types.ts
└── constants/
└── ai-analysis.constants.ts
```
### 文件职责
| 文件 | 职责 |
|------|------|
| `controller` | 接收创建分析任务、查询分析结果的接口 |
| `service` | 创建任务、查询状态、组织业务流程 |
| `repository` | 读写 AI 分析任务和分析结果 |
| `queue` | 封装 BullMQ 队列添加任务 |
| `processor` | 真正消费任务,调用大模型 |
| `jobs/xxx.job.ts` | 定义队列任务的数据结构 |
### AI 分析模块完整流程
```text
App 提交回答
Controller 接收请求
Service 创建分析任务
Repository 写入数据库 job 记录
Queue 加入 Redis 队列
Processor 后台消费任务
AI Service 调用大模型
Repository 写入分析结果
生成待巩固项
生成复习计划
通知用户
```
---
## 24. AI 层设计:不允许业务模块直接调大模型 SDK
### 原则
后面肯定会换模型、换供应商,所以 AI 不要写死在业务模块里。
**不推荐:**
```ts
// 不要直接在业务 service 里写
await openai.chat.completions.create(...)
```
**应该:**
```text
业务模块 → AiService → 具体 Provider
```
```ts
@Injectable()
export class AiService {
constructor(private readonly provider: AiProvider) {}
analyzeActiveRecall(input: ActiveRecallAnalysisInput) {
return this.provider.generateActiveRecallAnalysis(input);
}
}
```
这样从 OpenAI 换 DeepSeek、Gemini、Claude都不用改业务代码。
---
## 25. Infrastructure 层详细拆解
`infrastructure` 是所有模块共用的底层能力。
```text
infrastructure/
├── database/
│ ├── prisma.module.ts
│ └── prisma.service.ts
├── redis/
│ ├── redis.module.ts
│ ├── redis.service.ts
│ └── redis.constants.ts
├── queue/
│ ├── queue.module.ts
│ ├── queue.constants.ts
│ └── queue.service.ts
├── ai/
│ ├── ai.module.ts
│ ├── ai.service.ts
│ ├── ai-provider.interface.ts
│ ├── providers/
│ │ ├── openai.provider.ts
│ │ ├── deepseek.provider.ts
│ │ └── mock-ai.provider.ts
│ └── prompts/
│ ├── active-recall-analysis.prompt.ts
│ └── focus-item-generation.prompt.ts
├── storage/
│ ├── storage.module.ts
│ ├── storage.service.ts
│ └── local-storage.provider.ts
└── logger/
├── logger.module.ts
└── app-logger.service.ts
```
---
## 26. Common 层详细拆解
```text
common/
├── decorators/
│ └── current-user.decorator.ts
├── guards/
│ ├── jwt-auth.guard.ts
│ └── optional-auth.guard.ts
├── interceptors/
│ └── response.interceptor.ts
├── filters/
│ └── http-exception.filter.ts
├── pipes/
│ └── validation.pipe.ts
├── dto/
│ ├── pagination.dto.ts
│ └── api-response.dto.ts
├── types/
│ ├── user-payload.type.ts
│ └── pagination.type.ts
├── constants/
│ └── app.constants.ts
└── utils/
├── date.util.ts
├── hash.util.ts
└── id.util.ts
```
---
## 27. 模块复杂度分级
### 简单模块
结构 `module + controller + service + repository + dto`
适用于:`feedback``system``notifications`(初版)
### 中等模块
结构 `module + controller + service + repository + dto + types + constants`
适用于:`users``knowledge-base``knowledge-items``learning-session``review``focus-items`
### 复杂模块
结构 `module + controller + service + repository + queue + processor + jobs + dto + types + constants`
适用于:`ai-analysis``document-import``notifications`(后期)
---
## 28. 初始化顺序
第一版不要所有业务都写完。先搭基础设施骨架:
```text
1. infrastructure/database
2. infrastructure/redis
3. infrastructure/queue
4. infrastructure/ai
5. common
6. system/health
7. auth skeleton
8. users skeleton
9. knowledge-base skeleton
10. ai-analysis skeleton
```
这样就够开始开发。