You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
5.1 KiB
5.1 KiB
Changelog: 解析状态接口增强 - 包含 AI 任务状态
日期: 2026-02-11
类型: 功能增强
影响范围: 后端 API - 剧本解析状态查询
关联接口: GET /api/v1/screenplays/{screenplay_id}/parse-status
变更概述
修改 /parse-status 接口,同时返回文件解析状态和 AI 解析任务状态,只有当两者都完成时才返回 completed,避免前端过早查询 storyboards 导致数据为空。
问题背景
原有流程问题
前端流程:
1. POST /parse → 触发解析
2. 轮询 GET /parse-status → 等待 "completed"
3. 收到 "completed" → 立即调用 GET /storyboards
4. ❌ 问题:此时 AI 解析可能还未完成,storyboards 为空
根本原因
/parse-status原本只返回文件解析状态(提取文本内容)- 但 storyboards 是由 AI 解析任务创建的(提取角色/场景/道具/分镜)
- 两者是异步的,存在时间差
- 前端收到
completed时,AI 任务可能还在进行中
技术实现
修改文件
server/app/schemas/screenplay.py- 增强ParseStatusResponseserver/app/api/v1/screenplays.py- 修改get_parse_status接口
核心变更
1. Schema 增强
class ParseStatusResponse(BaseModel):
# 原有字段
screenplay_id: UUID
parsing_status: str # 综合状态
progress: int
message: str
# ✨ 新增字段
ai_job_id: Optional[UUID] # AI 任务 ID
ai_status: Optional[str] # AI 任务状态
ai_progress: Optional[int] # AI 任务进度
2. 状态综合判断逻辑
# 只有当文件解析完成 AND AI 任务完成时,才返回 completed
if parsing_status == COMPLETED:
if ai_status == 'pending':
final_status = 'parsing'
final_message = '等待 AI 解析...'
elif ai_status == 'processing':
final_status = 'parsing'
final_message = 'AI 正在提取角色、场景和道具...'
elif ai_status == 'completed':
final_status = 'completed' # ✅ 真正完成
final_message = '解析完成'
进度映射
| 阶段 | 进度 | 状态 | 说明 |
|---|---|---|---|
| 未开始 | 0% | idle | 初始状态 |
| 等待解析 | 10% | pending | 文件上传完成 |
| 解析文件 | 30% | parsing | 提取文本内容 |
| 等待 AI | 40% | parsing | 文件解析完成,等待 AI |
| AI 解析中 | 40-90% | parsing | AI 提取角色/场景/道具 |
| 完成 | 100% | completed | 文件 + AI 都完成 ✅ |
| 失败 | 0% | failed | 任一步骤失败 |
API 响应示例
解析中(AI 任务进行中)
{
"success": true,
"data": {
"screenplayId": "xxx",
"parsingStatus": "parsing",
"progress": 65,
"message": "AI 正在提取角色、场景和道具...",
"aiJobId": "yyy",
"aiStatus": "processing",
"aiProgress": 50
}
}
解析完成(AI 任务也完成)
{
"success": true,
"data": {
"screenplayId": "xxx",
"parsingStatus": "completed",
"progress": 100,
"message": "解析完成",
"wordCount": 356,
"fileUrl": "https://...",
"aiJobId": "yyy",
"aiStatus": "completed",
"aiProgress": 100
}
}
业务价值
1. 避免前端查询空数据
前端现在可以安全地等待 parsingStatus === 'completed' 后再查询 storyboards,确保数据已准备好。
2. 更准确的进度反馈
用户可以看到完整的解析流程:
- 文件解析(0-40%)
- AI 解析(40-90%)
- 完成(100%)
3. 更好的错误处理
可以区分文件解析失败和 AI 解析失败,提供更精确的错误信息。
向后兼容性
✅ 完全兼容 - 新增字段为可选,不影响现有前端
前端可以:
- 简单模式:只检查
parsingStatus === 'completed' - 详细模式:同时检查
aiStatus获取更多信息
测试验证
验证步骤
- 上传并解析一个剧本
- 轮询
/parse-status接口 - 观察状态变化:
pending→parsing→completed - 确认只有在 AI 任务完成后才返回
completed - 查询
/storyboards确认数据存在
预期结果
# 文件解析完成,但 AI 还在进行
GET /parse-status
→ parsingStatus: "parsing"
→ message: "AI 正在提取角色、场景和道具..."
→ aiStatus: "processing"
# AI 任务完成
GET /parse-status
→ parsingStatus: "completed"
→ message: "解析完成"
→ aiStatus: "completed"
# 此时查询 storyboards 有数据
GET /storyboards?project_id=xxx
→ 返回分镜列表 ✅
注意事项
- AI 任务查询:通过
input_data->>'screenplay_id'查询最近的 AI 任务 - 纯文本剧本:如果没有 AI 任务,文件解析完成即视为完成
- 进度计算:AI 进度映射到 40-90% 区间,避免进度倒退
后续优化
- 考虑在
screenplays表增加ai_job_id字段,避免每次查询 - 增加 WebSocket 推送,实时通知前端状态变化
- 支持批量查询多个剧本的解析状态
变更人: AI Assistant
审核人: 待审核
状态: ✅ 已实施