API-INFO-017 P0 | 首页继续学习接口 【status:todo】 #115

Closed
opened 2026-06-07 11:03:39 +08:00 by wangdl · 2 comments
Owner

目标

GET /learning/continue

规则

  • 查询 MaterialReadingProgress WHERE lastReadAt IS NOT NULL
  • ORDER BY lastReadAt DESC LIMIT 1
  • include/join 资料标题和知识库名称,避免 N+1
  • 过滤 deletedAt 不为空的 KnowledgeSource
  • 过滤过期 temporary_file
  • 无数据返回 type=none

详见设计文档 API-INFO-000。

## 目标 ```http GET /learning/continue ``` ### 规则 - 查询 MaterialReadingProgress WHERE lastReadAt IS NOT NULL - ORDER BY lastReadAt DESC LIMIT 1 - include/join 资料标题和知识库名称,避免 N+1 - 过滤 deletedAt 不为空的 KnowledgeSource - 过滤过期 temporary_file - 无数据返回 type=none 详见设计文档 API-INFO-000。
wangdl added this to the M8:学习信息收集与基础分析闭环 milestone 2026-06-07 11:03:39 +08:00
wangdl changed title from API-INFO-010 P0 | 首页继续学习接口 to API-INFO-017 P0 | 首页继续学习接口 2026-06-07 11:22:17 +08:00
wangdl changed title from API-INFO-017 P0 | 首页继续学习接口 to API-INFO-017 P0 | 首页继续学习接口 【status:todo】 2026-06-07 19:04:15 +08:00
Author
Owner

审查结论:当前 API 项目学习信息收集体系基本为全新建设。可复用:JWT Guard、LearningSession 基础表/CRUD、DailyLearningActivity 基础表、ActivityController 部分接口、LearningRecord schema。其余 ReadingEvent/TemporaryMaterial/Progress/批量上报/Processor/聚合/查询接口/错误码/去重/权限/测试/文档均不存在或仅部分存在。

本 Issue: 接口不存在。blocked-by:api-info-core

标签: audit:reviewed audit:api-info status:todo work:api

## 审查结论:当前 API 项目学习信息收集体系基本为全新建设。可复用:JWT Guard、LearningSession 基础表/CRUD、DailyLearningActivity 基础表、ActivityController 部分接口、LearningRecord schema。其余 ReadingEvent/TemporaryMaterial/Progress/批量上报/Processor/聚合/查询接口/错误码/去重/权限/测试/文档均不存在或仅部分存在。 **本 Issue**: 接口不存在。blocked-by:api-info-core **标签**: audit:reviewed audit:api-info status:todo work:api
Author
Owner

完成报告

交付

GET /learning/continue — 首页继续学习:

@Get("learning/continue")
async continueLearning(req) {
  // 查询最新阅读进度的资料
  const latest = await prisma.materialReadingProgress.findFirst({
    where: { userId, lastReadAt: { not: null }, status: { in: ["reading", "read"] } },
    orderBy: { lastReadAt: "desc" },
  });

  // knowledge_source: join KnowledgeSource 获取 title, 过滤 deletedAt
  // 无数据: { type: "none" }
}

Response:

// 有数据:
{ "type": "knowledge_source", "materialId": "cuid_mat_001", "title": "Document Title",
  "lastPosition": {...}, "lastProgress": 0.5, "totalActiveSeconds": 120, "lastReadAt": "..." }

// 无数据:
{ "type": "none" }

规则实现:

  • ORDER BY lastReadAt DESC LIMIT 1
  • 过滤 status IN (reading, read)
  • knowledge_source 过滤 deletedAt
  • include 标题(避免 N+1:单次查询)
  • 无数据返回 type=none
## 完成报告 ### 交付 **`GET /learning/continue`** — 首页继续学习: ```typescript @Get("learning/continue") async continueLearning(req) { // 查询最新阅读进度的资料 const latest = await prisma.materialReadingProgress.findFirst({ where: { userId, lastReadAt: { not: null }, status: { in: ["reading", "read"] } }, orderBy: { lastReadAt: "desc" }, }); // knowledge_source: join KnowledgeSource 获取 title, 过滤 deletedAt // 无数据: { type: "none" } } ``` **Response:** ```json // 有数据: { "type": "knowledge_source", "materialId": "cuid_mat_001", "title": "Document Title", "lastPosition": {...}, "lastProgress": 0.5, "totalActiveSeconds": 120, "lastReadAt": "..." } // 无数据: { "type": "none" } ``` **规则实现:** - ✅ ORDER BY lastReadAt DESC LIMIT 1 - ✅ 过滤 status IN (reading, read) - ✅ knowledge_source 过滤 deletedAt - ✅ include 标题(避免 N+1:单次查询) - ✅ 无数据返回 type=none
Sign in to join this conversation.
No Label
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: wangdl/api-server#115
No description provided.