Files
label_ai_service/specs/001-ai-service-requirements/spec.md
wh e0d080ceea feat: add AI service requirements spec (001-ai-service-requirements)
- 8 user stories (P1-P3): text triple extraction, image quadruple extraction,
  video frame extraction, video-to-text, QA generation (text/image),
  finetune management, health check
- 18 functional requirements covering all 8 API endpoints
- 9 success criteria with measurable metrics
- Technical environment section: Python 3.12.13, FastAPI, conda label env
- Quality checklist: all items pass
2026-04-10 14:51:34 +08:00

20 KiB
Raw Blame History

Feature Specification: AI 服务需求文档

Feature Branch: 001-ai-service-requirements
Created: 2026-04-10
Status: Draft
Input: User description: "@docs/superpowers/specs/2026-04-10-ai-service-design.md 根据设计文档完成需求文档"


概述

知识图谱智能标注平台需要一个独立的 AI 计算服务,接收 Java 后端的调用,完成文档结构化提取、图像分析、视频预处理、训练数据生成和模型微调管理等智能化任务,将大模型能力嵌入标注工作流,大幅降低人工标注成本。


User Scenarios & Testing (mandatory)

User Story 1 - ADMIN 从文档中提取知识三元组 (Priority: P1)

ADMIN 在标注平台上选择一份已上传的文本文件TXT、PDF 或 Word 文档),触发 AI 辅助提取。AI 服务从存储系统中读取该文档,分析内容,识别其中的主谓宾知识关系(三元组),并为每个三元组标注原文出处片段和字符偏移位置,返回结构化结果供标注员审核确认。

Why this priority: 文本三元组提取是平台文本标注流水线的核心入口,所有文本类标注任务都依赖此能力。无此功能,平台的主要价值无法实现。

Independent Test: 向 AI 服务发送一个包含已知知识点的测试文档路径,验证返回结果包含正确的主语/谓语/宾语和对应的原文位置信息,即可独立验证此功能完整运行。

Acceptance Scenarios:

  1. Given 存储系统中存有一份 TXT 格式文档,When AI 服务收到该文档路径和提取请求,Then 返回包含至少一条三元组的结果,每条含 subject、predicate、object、原文片段和字符偏移。
  2. Given 存储系统中存有一份 PDF 格式文档,When AI 服务收到提取请求,Then 正确解析 PDF 内容并返回三元组结果。
  3. Given 存储系统中存有一份 Word.docx格式文档When AI 服务收到提取请求,Then 正确解析文档内容并返回三元组结果。
  4. Given 请求包含不支持的文件格式(如 .xlsxWhen AI 服务收到请求,Then 返回明确的格式不支持错误,不崩溃。
  5. Given 存储系统不可达,When AI 服务尝试下载文件,Then 返回存储故障错误,而非通用服务器错误。

User Story 2 - ADMIN 从图片中提取知识四元组并自动裁剪 (Priority: P1)

ADMIN 在标注平台选择一张已上传的图片,触发 AI 辅助提取。AI 服务读取该图片通过多模态大模型分析图像内容识别图中的知识实体关系四元组主体、关系、客体、修饰信息同时给出每个知识点在图像中的位置框bbox 坐标),并自动将对应区域裁剪保存,供标注员对照审核。

Why this priority: 图像四元组提取是图片标注流水线的核心入口,与文本三元组提取并列为平台两大主流水线的起点。

Independent Test: 向 AI 服务发送一张包含可识别对象关系的测试图片路径,验证返回结果包含四元组信息和裁剪图的存储路径,即可独立验证此功能完整运行。

Acceptance Scenarios:

  1. Given 存储系统中存有一张图片,When AI 服务收到该图片路径和提取请求,Then 返回包含至少一条四元组的结果,每条含 subject、predicate、object、qualifier 和 bbox 坐标。
  2. Given AI 服务成功提取四元组,When 处理完成,Then 每个四元组对应的图像区域已自动裁剪并上传至存储,响应中包含裁剪图的存储路径。
  3. Given bbox 坐标超出图像边界,When 裁剪时,Then 自动截断至图像有效区域,不报错。
  4. Given 大模型返回格式异常(非 JSONWhen 解析响应,Then 返回解析失败错误,不返回部分结果。

User Story 3 - ADMIN 对视频进行帧提取(帧模式预处理) (Priority: P2)

ADMIN 在标注平台选择一段已上传的视频,选择"帧提取"模式(按固定间隔或关键帧),触发 AI 服务处理。AI 服务在后台异步完成帧提取,将每一帧图片上传至存储,处理完成后主动通知 Java 后端,后端随即为每一帧创建图片标注任务,进入图片标注流程。

Why this priority: 视频帧提取是视频进入图片标注流水线的预处理步骤依赖图片提取流水线P1已就绪。

Independent Test: 向 AI 服务发送一个测试视频的存储路径和 job_id服务立即返回 202 Accepted稍后验证回调接口收到含帧路径列表的成功通知即可独立验证。

Acceptance Scenarios:

  1. Given 存储系统中存有一段视频(大小在限制内),When AI 服务收到帧提取请求interval 模式),Then 立即返回 202 Accepted 和 job_id不等待处理完成。
  2. Given 帧提取任务在后台成功完成,When 处理完成,Then AI 服务向 Java 后端发送回调,包含 job_id、status=SUCCESS 和帧图存储路径列表。
  3. Given keyframe 模式,When AI 服务处理视频,Then 仅提取画面发生显著变化的帧,而非固定间隔。
  4. Given 视频文件大小超过系统上限(默认 200MB可配置When 收到请求,Then 立即返回 400 错误,不启动后台任务。
  5. Given 帧提取过程中发生错误,When 任务失败,Then AI 服务仍向 Java 后端发送回调status=FAILED包含错误描述。

User Story 4 - ADMIN 将视频片段转换为文字描述(片段模式预处理) (Priority: P2)

ADMIN 在标注平台选择一段已上传视频的时间段,触发"视频转文本"预处理。AI 服务在后台均匀采样该时间段的视频帧,用多模态大模型理解视频内容,生成结构化文字描述,将描述文本上传存储,完成后通知 Java 后端,后端将其创建为新的文本类原始资料,进入文本标注流程。

Why this priority: 视频转文本预处理使视频内容能够通过文本标注流水线处理,扩展了平台的数据来源范围。

Independent Test: 向 AI 服务发送测试视频路径、时间段和 job_id验证回调收到 output_path 指向一个可读的文字描述文件,即可独立验证。

Acceptance Scenarios:

  1. Given 存储系统中存有一段视频(大小在限制内),When AI 服务收到视频转文本请求,Then 立即返回 202 Accepted 和 job_id。
  2. Given 视频转文本任务在后台成功完成,When 处理完成,Then AI 服务向 Java 后端发送回调,包含 job_id、status=SUCCESS 和文字描述的存储路径。
  3. Given 请求指定了起止时间段start_sec、end_secWhen 处理视频,Then 仅分析该时间段内的内容,不处理其他片段。
  4. Given 视频文件大小超过上限,When 收到请求,Then 立即返回 400 错误。
  5. Given 大模型调用失败,When 任务异常,Then 回调 status=FAILED包含错误描述。

User Story 5 - 系统自动为已审批三元组生成候选问答对 (Priority: P2)

标注员提交的文本三元组经审批员审批通过后,系统自动调用 AI 服务,将三元组列表和对应原文片段批量输入大模型,生成符合微调格式的候选问答对,作为后续训练数据的来源。

Why this priority: 问答对生成是平台训练数据产出流程的关键环节依赖三元组提取P1已完成并通过审批。

Independent Test: 向 AI 服务发送一组测试三元组(含原文片段),验证返回包含可读、合理的问答对列表,即可独立验证。

Acceptance Scenarios:

  1. Given 一组已审批的文本三元组,When AI 服务收到文本 QA 生成请求,Then 返回包含 question 和 answer 的问答对列表,每个三元组至少对应一个问答对。
  2. Given 大模型返回合法 JSONWhen 解析响应,Then 正确提取每对问答并返回。
  3. Given 大模型返回格式异常,When 解析响应,Then 返回解析失败错误。
  4. Given 大模型服务不可用,When 调用失败,Then 返回明确的服务不可用错误。

User Story 6 - 系统自动为已审批四元组生成候选图文问答对 (Priority: P2)

图像四元组经审批通过后,系统自动调用 AI 服务,将四元组信息与对应裁剪图一起输入多模态大模型,生成图文问答对,用于后续图像类训练数据集。

Why this priority: 图像 QA 生成是图片标注流水线产出训练数据的最终步骤,优先级与文本 QA 生成P2相同。

Independent Test: 向 AI 服务发送一组四元组(含裁剪图存储路径),验证返回的问答对引用了图片路径,即可独立验证。

Acceptance Scenarios:

  1. Given 一组已审批的图像四元组(含裁剪图路径),When AI 服务收到图像 QA 生成请求,Then 返回包含 question、answer 和 image_path 的问答对列表。
  2. Given 裁剪图存储路径有效,When AI 服务处理,Then 自动获取图片内容并结合四元组信息生成问答,无需调用方额外传输图片数据。
  3. Given 裁剪图无法从存储获取,When 处理请求,Then 返回存储错误,不返回空结果。

User Story 7 - ADMIN 提交微调任务并查询进度 (Priority: P3)

ADMIN 在标注平台完成训练数据集导出后,选择提交大模型微调任务。平台调用 AI 服务提交微调请求(包含训练数据文件地址、基础模型和超参数),获取微调任务 ID。此后ADMIN 可随时查询该任务的运行状态(进行中/成功/失败)和完成进度。

Why this priority: 微调任务管理是平台最终目标(产出定制化模型)的关键步骤,但需要前置数据准备流程全部完成,故列为 P3。

Independent Test: 向 AI 服务发送微调请求,获取 job_id再调用状态查询接口验证能正确返回当前状态即可独立验证。

Acceptance Scenarios:

  1. Given 训练数据 JSONL 文件已在存储中准备就绪,When AI 服务收到微调提交请求(含文件地址、基础模型、超参数),Then 返回微调任务 ID。
  2. Given 微调任务已提交,When 查询任务状态,Then 返回 job_id、当前状态RUNNING/SUCCESS/FAILED和进度百分比。
  3. Given 任务处于运行中,When 多次查询状态,Then 每次均返回最新状态,不缓存旧状态。
  4. Given 传入不存在的 job_id 查询状态,When 处理请求,Then 返回明确错误,不崩溃。

User Story 8 - 运维监控服务健康状态 (Priority: P3)

运维人员或监控系统定期探测 AI 服务的健康状态,判断服务是否正常运行,以便在异常时及时告警或自动重启。

Why this priority: 健康检查是服务稳定运行的基础保障,但不属于业务功能,列为 P3。

Independent Test: 对健康检查接口发起 HTTP GET 请求,验证收到表示正常的响应,即可独立验证。

Acceptance Scenarios:

  1. Given AI 服务正常运行,When 任何系统对健康检查接口发起请求,Then 立即返回服务正常的响应,响应时间不超过 1 秒。
  2. Given 容器运行中,When 容器编排系统定期发起健康探测,Then 通过探测的容器才被标记为可用状态并接收流量。

Edge Cases

  • 文件存在于存储系统但内容损坏(如 PDF 页面为空)时,如何处理?→ 返回解析结果为空,不报错,日志记录警告。
  • 视频帧提取结果为零帧(如视频文件损坏或间隔过大)时,如何处理?→ 回调 SUCCESS返回空帧列表Java 后端决定是否重试。
  • 大模型返回的三元组/四元组超过合理数量(如数百条)时,如何处理?→ 全量返回,由 Java 后端或标注员筛选AI 服务不做截断。
  • 多个视频任务并发执行时,是否会互相影响?→ 每个任务独立使用临时文件,处理完成后清理,互不干扰。
  • 视频文件大小恰好等于上限时,如何处理?→ 视为超限,拒绝处理,避免边界情况下的内存压力。
  • 大模型以 Markdown 代码块格式(```json ... ```)返回 JSON 时,如何处理?→ 自动提取代码块内的 JSON 内容,兼容此格式。

Requirements (mandatory)

Functional Requirements

文本处理

  • FR-001: 系统 MUST 支持从 TXT、PDF、DOCX 三种格式的文档中提取知识三元组subject / predicate / object并为每条三元组提供原文出处片段和字符偏移位置。
  • FR-002: 系统 MUST 在文件格式不受支持时返回明确的格式不支持错误HTTP 400拒绝处理请求。

图像处理

  • FR-003: 系统 MUST 支持从图片中提取知识四元组subject / predicate / object / qualifier并提供每个知识点在图像中的位置框bboxx, y, w, h 像素坐标)。
  • FR-004: 系统 MUST 在返回四元组结果时,自动将每个知识点对应的图像区域裁剪并保存至存储,响应中包含裁剪图的存储路径。

视频处理

  • FR-005: 系统 MUST 支持视频帧提取,提供两种模式:固定间隔模式(按帧数间隔)和关键帧模式(场景切换时提取)。
  • FR-006: 系统 MUST 以异步方式处理视频任务接受请求后立即返回接受确认HTTP 202在后台完成处理后主动通知调用方。
  • FR-007: 系统 MUST 支持视频片段转文字描述,输入起止时间段,输出视频内容的结构化文字描述,并将描述文本保存至存储。
  • FR-008: 系统 MUST 在视频文件大小超过上限时,拒绝处理并返回明确错误;大小上限 MUST 支持运行时配置(默认 200MB不需要重新构建服务即可调整。

问答对生成

  • FR-009: 系统 MUST 支持基于文本三元组(含原文片段)批量生成候选问答对,每条三元组至少生成一个问答对。
  • FR-010: 系统 MUST 支持基于图像四元组(含裁剪图存储路径)生成图文候选问答对,图片内容由系统自动从存储获取,调用方只需提供存储路径。

微调管理

  • FR-011: 系统 MUST 支持向大模型服务提交微调任务,输入训练数据文件地址、基础模型名称和超参数,返回微调任务 ID。
  • FR-012: 系统 MUST 支持通过任务 ID 查询微调任务当前状态RUNNING / SUCCESS / FAILED和完成进度。

服务运维

  • FR-013: 系统 MUST 提供轻量健康检查接口,可被容器编排系统、反向代理和监控工具调用,无需认证,响应时间不超过 1 秒。
  • FR-014: 系统 MUST 对每次请求记录结构化日志,包含请求路径、响应状态和耗时;对每次大模型调用记录模型名称和耗时;对视频后台任务记录任务 ID、阶段和结果日志 MUST NOT 包含文件原文内容。
  • FR-015: 系统 MUST 在大模型返回非法格式时HTTP 502、存储不可达时HTTP 502、大模型服务不可用时HTTP 503分别返回不同的结构化错误响应便于调用方判断根因。
  • FR-016: 系统 MUST 提供 Swagger/OpenAPI 自动文档,描述所有接口的请求和响应格式。

可扩展性

  • FR-017: 系统 MUST 将大模型调用和存储访问封装为可替换的适配层,当前实现 ZhipuAI GLM 系列和 RustFS替换实现时业务逻辑层无需修改。
  • FR-018: 系统 MUST 通过配置文件和环境变量管理所有可变参数(模型名称、存储地址、密钥、视频大小上限等),支持不重建服务镜像的情况下切换环境配置。

Key Entities

  • 三元组Triple: 从文本中提取的知识关系由主语subject、谓语predicate、宾语object、原文片段source_snippet和字符偏移source_offset: start/end组成。
  • 四元组Quadruple: 从图像中提取的知识关系在三元组基础上增加修饰信息qualifier和图像位置框bbox: x/y/w/h并关联裁剪图存储路径cropped_image_path
  • 问答对QA Pair: 由 question 和 answer 组成文本类关联三元组上下文图像类额外携带图片存储路径image_path
  • 视频任务回调Video Job Callback: 异步任务完成通知,包含 job_id、statusSUCCESS/FAILED、结果数据帧路径列表或文字描述路径和错误信息。
  • 微调任务Finetune Job: 包含任务 ID、当前状态RUNNING/SUCCESS/FAILED和进度百分比。

Success Criteria (mandatory)

Measurable Outcomes

  • SC-001: 对于长度在 10,000 字以内的文档,三元组提取请求在 60 秒内完成并返回结果,满足标注员实时等待的体验预期。
  • SC-002: 对于分辨率在 4K 以内的图片,四元组提取和裁剪图上传在 30 秒内完成,裁剪图区域与 bbox 坐标对应准确(误差 ≤2 像素)。
  • SC-003: 视频帧提取和视频转文本任务提交后,接受响应在 1 秒内返回;后台处理完成后回调通知在 10 分钟内送达(针对 200MB 以内的视频)。
  • SC-004: 视频大小超限的请求,拒绝响应在 3 秒内返回(含存储查询耗时),不启动任何后台处理。
  • SC-005: 问答对生成请求≤10 条三元组/四元组),在 90 秒内完成并返回全部问答对。
  • SC-006: 健康检查接口在服务正常运行时,响应时间不超过 1 秒,容器编排系统依此判断服务可用状态。
  • SC-007: 所有错误响应均返回结构化错误信息(含错误类型和描述),不返回通用服务器错误,便于调用方在不查看日志的情况下判断根因。
  • SC-008: 替换大模型服务商或存储实现时,业务逻辑层代码零修改,仅需变更配置和适配层实现。
  • SC-009: 所有业务接口通过自动化单元测试覆盖,包括正常路径、存储错误、大模型错误、格式解析错误等场景。

Technical Environment (mandatory)

注:本节记录项目已确定的技术约束,这些决定已由团队确认,不作为需求变更点。

  • 运行时: Python 3.12.13
  • Web 框架: FastAPI含 uvicorn 服务器)
  • 运行环境: conda 虚拟环境,环境名称 label
  • 大模型: ZhipuAI GLM 系列文本glm-4-flash视觉glm-4v-flash通过官方 SDK 调用
  • 对象存储: RustFS通过 S3 兼容 APIboto3访问
  • 文档解析: TXTUTF-8 解码、PDFpdfplumber、DOCXpython-docx
  • 视频处理: OpenCV帧提取 + 帧差分关键帧检测)
  • 容器化: Docker + Docker Compose提供 Dockerfile 和 docker-compose.yml

Assumptions

  • Java 后端label-backend是 AI 服务的唯一调用方AI 服务不对外直接暴露,无需用户认证机制。
  • 大模型服务部署在公网ZhipuAI 云端 APIRustFS 部署在 Docker 内网;因此图片内容必须以 base64 方式传递给大模型,不能依赖 RustFS 内网地址被云端服务访问。
  • 文档、图片、视频等原始文件由 Java 后端负责上传至存储AI 服务仅通过存储路径读取,不处理文件上传逻辑。
  • 微调任务提交后的训练过程由 ZhipuAI 平台托管AI 服务仅负责提交和查询,不管理训练算力资源。
  • 视频任务为低频操作(由 ADMIN 手动触发),并发量有限(预计同时不超过 5 个视频任务),当前无需专用任务队列。
  • 日志仅输出到标准输出stdout由容器运行时或日志收集系统负责落盘和归档不记录文件原文内容防止敏感信息泄露。
  • ZhipuAI SDK 为同步阻塞调用为保持服务并发能力SDK 调用将在线程池中执行,不阻塞主事件循环。
  • 视频大小上限默认 200MB可通过环境变量MAX_VIDEO_SIZE_MB在容器运行时覆盖无需重建镜像。