From fa94e5a76fb794673ee5eeacd67346db68bf17b1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E7=81=B5=E5=BA=94?= Date: Wed, 8 Jul 2026 16:30:29 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20=E7=94=9F=E6=88=90=E5=85=9C=E5=BA=95?= =?UTF-8?q?=E9=80=BB=E8=BE=91=E5=9B=9E=E9=80=80=E6=97=A7=E6=A8=A1=E5=9E=8B?= =?UTF-8?q?template=5Fsegments?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 根因:模板片段配置存在template_segments表(旧模型),但兜底逻辑读的是 template_clip_configs表(新模型,空表),导致0片段→can_generate失败→400。 修复:优先读新模型,无数据时回退读旧模型template_segments,确保兜底生效。 --- apps/api/app/api/routes/edit_plans.py | 46 ++++++++++++++++++++------- 1 file changed, 34 insertions(+), 12 deletions(-) diff --git a/apps/api/app/api/routes/edit_plans.py b/apps/api/app/api/routes/edit_plans.py index 46f2036d1..e5b5a3199 100644 --- a/apps/api/app/api/routes/edit_plans.py +++ b/apps/api/app/api/routes/edit_plans.py @@ -35,6 +35,9 @@ from packages.adapters.sqlalchemy_impl.generation_task_repository import ( from packages.adapters.sqlalchemy_impl.template_clip_config_repository import ( SQLAlchemyTemplateClipConfigRepository, ) +from packages.adapters.sqlalchemy_impl.template_repository import ( + SQLAlchemyTemplateRepository, +) from packages.application.generation_tasks import ( CreateGenerationTaskCommand, CreateGenerationTaskUseCase, @@ -470,20 +473,39 @@ def generate_plan( plan_id, plan_check.template_id, ) + # 优先从新模型 template_clip_configs 读取,若无则回退到旧模型 template_segments clip_config_repo = SQLAlchemyTemplateClipConfigRepository(db) configs = clip_config_repo.list_by_template(plan_check.template_id) - for cfg in configs: - svc.create_clip( - plan_id=plan_id, - clip_type=cfg.clip_type.value if hasattr(cfg.clip_type, "value") else cfg.clip_type, - order=cfg.order, - template_clip_config_id=cfg.id, - duration=cfg.default_duration, - transition_effect=( - cfg.transition_effect.value if hasattr(cfg.transition_effect, "value") else cfg.transition_effect - ), - ) - logger.info("自动兜底: plan=%s 从模板复制了 %d 个片段", plan_id, len(configs)) + if configs: + for cfg in configs: + svc.create_clip( + plan_id=plan_id, + clip_type=cfg.clip_type.value if hasattr(cfg.clip_type, "value") else cfg.clip_type, + order=cfg.order, + template_clip_config_id=cfg.id, + duration=cfg.default_duration, + transition_effect=( + cfg.transition_effect.value if hasattr(cfg.transition_effect, "value") else cfg.transition_effect + ), + ) + logger.info("自动兜底: plan=%s 从新模型 template_clip_configs 复制了 %d 个片段", plan_id, len(configs)) + else: + # 回退到旧模型 template_segments + tpl_repo = SQLAlchemyTemplateRepository(db) + segments = tpl_repo.list_segments(plan_check.template_id) + for seg in segments: + avg_duration = (seg.duration_min + seg.duration_max) / 2 + svc.create_clip( + plan_id=plan_id, + clip_type="main", # 旧模型无结构角色,统一为主体片段 + order=seg.segment_order, + duration=avg_duration, + config={ + "material_type": seg.material_type or "", + "template_segment_id": seg.id, + }, + ) + logger.info("自动兜底: plan=%s 从旧模型 template_segments 复制了 %d 个片段", plan_id, len(segments)) # 检查是否可生成 try: