fix(pipeline): 视频为末步时收口项目完成态 + 列表 5→4 步同步
V1 雪藏「拼接导出」第 5 阶段后,完成态(COMPLETED)只在 export.py 拼接成片时 才置,导致视频全部出片的项目永远卡在 videoing,列表末格一直闪烁。 - 后端:新增 settle_video_completion(幂等)+ VIDEO_IS_FINAL_STAGE 开关。 全部片段出片→项目 completed、video 阶段标成功;某段被重跑→退回 videoing。 挂 retrieve(自愈历史卡住项目)/poll-video-segment/submit-video-segment/ adopt-video-version 四入口;收口直接查库,不吃 prefetch 旧缓存致误判。 V2 恢复导出把 VIDEO_IS_FINAL_STAGE 置 False,完成判定交回 export.py。 - 前端:项目列表/网格进度从 5 步同步成 4 步(PROJ_STAGE_TOTAL=4), export 阶段并入第 4;已完成项目末格走 done(绿)不再用闪烁的 cur。 Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -361,9 +361,21 @@ export function ProjectWizardPage({ products, projects = [], preselectProductId,
|
||||
);
|
||||
}
|
||||
|
||||
// 对齐 api-bridge:阶段编号 / 状态分桶 / 友好标签 / pill 类
|
||||
const PROJ_STAGE_NO: Record<string, number> = { script: 1, base_assets: 2, storyboard: 3, video: 4, export: 5 };
|
||||
function projStageNo(project: Project) { return project.status === "completed" ? 5 : (PROJ_STAGE_NO[project.current_stage] || 1); }
|
||||
// 对齐 api-bridge / pipeline:阶段编号 / 状态分桶 / 友好标签 / pill 类
|
||||
// V1 雪藏「拼接导出」第 5 阶段(代码保留,V2 恢复):流程现为 4 步,export 归并到第 4(视频),
|
||||
// 已完成项目落到第 4 阶段而非被藏的第 5。(与 pipeline.tsx STAGE_STEPS / projectStage 对齐)
|
||||
const PROJ_STAGE_TOTAL = 4;
|
||||
const PROJ_STAGE_NO: Record<string, number> = { script: 1, base_assets: 2, storyboard: 3, video: 4, export: 4 };
|
||||
function projStageNo(project: Project) { return project.status === "completed" ? PROJ_STAGE_TOTAL : (PROJ_STAGE_NO[project.current_stage] || 1); }
|
||||
// 进度格 class:
|
||||
// · 已完成 → 含末格在内全部 done(绿),末格不再用闪烁的 cur
|
||||
// · 失败 → 停在第 no 格标红(fail),之前的 done
|
||||
// · 进行中 → 已过的格 done,当前格 cur(一闪一闪),未到的格留空
|
||||
function projProgClass(project: Project, i: number, no: number): string {
|
||||
if (project.status === "completed") return i <= no ? "done" : "";
|
||||
if (project.status === "failed") return i === no ? "fail" : i < no ? "done" : "";
|
||||
return i < no ? "done" : i === no ? "cur" : "";
|
||||
}
|
||||
function projBucket(project: Project) { return project.status === "completed" ? "done" : project.status === "failed" ? "fail" : "wip"; }
|
||||
function projStatusLabel(project: Project) {
|
||||
return ({ draft: "脚本待生成", scripting: "脚本生成中", asseting: "基础资产生成中", storyboarding: "故事板生成中", videoing: "视频片段生成中", exporting: "导出中", completed: "已完成", failed: "失败" } as Record<string, string>)[project.status] || "进行中";
|
||||
@@ -644,8 +656,8 @@ export function ProjectsPage({ products, projects, loading = false, navigate, op
|
||||
<td><span className="muted">{(project.script_version_count ?? project.script_versions?.length ?? 0) > 0 ? "AI 已生成" : "暂无脚本"}</span></td>
|
||||
<td>
|
||||
<div className="hstack">
|
||||
<div className="prog">{[1, 2, 3, 4, 5].map((i) => <span key={i} className={project.status === "failed" && i === no ? "fail" : i < no ? "done" : i === no ? "cur" : ""} />)}</div>
|
||||
<span className="muted-2 mono" style={{ fontSize: "12px" }}>{no}/5</span>
|
||||
<div className="prog">{Array.from({ length: PROJ_STAGE_TOTAL }, (_, k) => k + 1).map((i) => <span key={i} className={projProgClass(project, i, no)} />)}</div>
|
||||
<span className="muted-2 mono" style={{ fontSize: "12px" }}>{no}/{PROJ_STAGE_TOTAL}</span>
|
||||
</div>
|
||||
</td>
|
||||
<td><span className={`pill ${projPillClass(project)}`}><span className="dot" />{projStatusLabel(project)}</span></td>
|
||||
@@ -683,8 +695,8 @@ export function ProjectsPage({ products, projects, loading = false, navigate, op
|
||||
<div className="card-sub">{productTitle(project.product)} · {projShots(project)} 镜</div>
|
||||
</div>
|
||||
<div className="hstack">
|
||||
<div className="prog">{[1, 2, 3, 4, 5].map((i) => <span key={i} className={project.status === "failed" && i === no ? "fail" : i < no ? "done" : i === no ? "cur" : ""} />)}</div>
|
||||
<span className="muted-2 mono" style={{ fontSize: "10.5px" }}>{no}/5</span>
|
||||
<div className="prog">{Array.from({ length: PROJ_STAGE_TOTAL }, (_, k) => k + 1).map((i) => <span key={i} className={projProgClass(project, i, no)} />)}</div>
|
||||
<span className="muted-2 mono" style={{ fontSize: "10.5px" }}>{no}/{PROJ_STAGE_TOTAL}</span>
|
||||
</div>
|
||||
<div className="card-foot"><span className={`pill ${projPillClass(project)}`}><span className="dot" />{projStatusLabel(project)}</span><span className="card-time">{projDate(project)}</span></div>
|
||||
</div>
|
||||
|
||||
Reference in New Issue
Block a user