788559ff29
CI/CD Pipeline / Frontend Lint (push) Successful in 48s
CI/CD Pipeline / Validate Code Quality And Tests (push) Successful in 1m6s
CI/CD Pipeline / Build Production Runtime Images (push) Has been skipped
CI/CD Pipeline / Deploy Production (push) Has been skipped
CI/CD Pipeline / Production Browser E2E (push) Has been skipped
CI/CD Pipeline / Integration Tests (push) Successful in 1m22s
CI/CD Pipeline / Build & Push Staging (Watchtower auto-deploy) (push) Successful in 53m17s
CI/CD Pipeline / Staging E2E Tests (push) Successful in 1m10s
CI/CD Pipeline / Staging API Integration Tests (push) Successful in 3m16s
258 lines
8.1 KiB
Python
258 lines
8.1 KiB
Python
"""灰度对比测试场景定义 — 覆盖典型渲染场景.
|
||
|
||
每个场景对应一个 EditPlan,用于新旧引擎对比。
|
||
覆盖场景:
|
||
1. 简单直通(单clip无特效)
|
||
2. 多clip转场(fade + slide)
|
||
3. 画中画(main + overlay)
|
||
4. 字幕渲染(ASS字幕)
|
||
5. 独立音频轨(主视频 + BGM)
|
||
6. 多图层混合(main + broll + overlay + audio)
|
||
7. 背景图片 + 主视频(图片背景无音频)
|
||
8. 无音频视频(纯画面,验证无音轨防御)
|
||
9. 长视频(10+ clip,压力测试)
|
||
10. 分辨率非标(竖屏9:16,验证scale策略)
|
||
"""
|
||
|
||
from __future__ import annotations
|
||
|
||
from dataclasses import dataclass, field
|
||
from typing import Any
|
||
|
||
|
||
@dataclass
|
||
class CompareScenario:
|
||
"""对比测试场景."""
|
||
|
||
id: str
|
||
name: str
|
||
description: str
|
||
priority: str # P0 / P1 / P2
|
||
plan_payload: dict[str, Any] # EditPlan JSON payload(提交给 API 的数据)
|
||
expected: dict[str, Any] = field(default_factory=dict) # 预期结果
|
||
|
||
|
||
SCENARIOS: list[CompareScenario] = [
|
||
CompareScenario(
|
||
id="simple_pass_through",
|
||
name="简单直通",
|
||
description="单主clip,无转场无特效,验证直通优化路径",
|
||
priority="P0",
|
||
plan_payload={
|
||
"width": 1280,
|
||
"height": 720,
|
||
"fps": 25,
|
||
"clips": [
|
||
{
|
||
"clip_type": "main",
|
||
"asset_id": "sample_5s.mp4",
|
||
"duration": 5.0,
|
||
"order": 0,
|
||
}
|
||
],
|
||
},
|
||
),
|
||
CompareScenario(
|
||
id="multi_clip_transition",
|
||
name="多clip转场",
|
||
description="3个clip,fade + slideleft 转场",
|
||
priority="P0",
|
||
plan_payload={
|
||
"width": 1280,
|
||
"height": 720,
|
||
"fps": 25,
|
||
"clips": [
|
||
{
|
||
"clip_type": "main",
|
||
"asset_id": "sample_5s.mp4",
|
||
"duration": 3.0,
|
||
"order": 0,
|
||
"transition_effect": "cut",
|
||
},
|
||
{
|
||
"clip_type": "main",
|
||
"asset_id": "sample_5s.mp4",
|
||
"duration": 3.0,
|
||
"order": 1,
|
||
"transition_effect": "fade",
|
||
},
|
||
{
|
||
"clip_type": "main",
|
||
"asset_id": "sample_5s.mp4",
|
||
"duration": 3.0,
|
||
"order": 2,
|
||
"transition_effect": "slideleft",
|
||
},
|
||
],
|
||
},
|
||
),
|
||
CompareScenario(
|
||
id="picture_in_picture",
|
||
name="画中画",
|
||
description="主视频 + 角落小窗(corner_voice)",
|
||
priority="P1",
|
||
plan_payload={
|
||
"width": 1280,
|
||
"height": 720,
|
||
"fps": 25,
|
||
"clips": [
|
||
{"clip_type": "main", "asset_id": "sample_5s.mp4", "duration": 5.0, "order": 0},
|
||
{"clip_type": "corner_voice", "asset_id": "sample_5s.mp4", "duration": 5.0, "order": 0},
|
||
],
|
||
},
|
||
),
|
||
CompareScenario(
|
||
id="subtitle_rendering",
|
||
name="字幕渲染",
|
||
description="主视频 + ASS字幕",
|
||
priority="P0",
|
||
plan_payload={
|
||
"width": 1280,
|
||
"height": 720,
|
||
"fps": 25,
|
||
"clips": [
|
||
{
|
||
"clip_type": "main",
|
||
"asset_id": "sample_5s.mp4",
|
||
"duration": 5.0,
|
||
"order": 0,
|
||
"config": {"subtitles": [{"text": "测试字幕 Test Subtitle", "start_time": 0, "end_time": 5.0}]},
|
||
}
|
||
],
|
||
},
|
||
),
|
||
CompareScenario(
|
||
id="independent_audio_track",
|
||
name="独立音频轨",
|
||
description="主视频(带音频)+ 独立BGM轨,验证音频混音",
|
||
priority="P0",
|
||
plan_payload={
|
||
"width": 1280,
|
||
"height": 720,
|
||
"fps": 25,
|
||
"clips": [
|
||
{"clip_type": "main", "asset_id": "sample_5s.mp4", "duration": 5.0, "order": 0},
|
||
{
|
||
"clip_type": "main",
|
||
"asset_id": "sample_bgm.mp3",
|
||
"duration": 5.0,
|
||
"order": 0,
|
||
"config": {"role": "audio", "volume": 0.5},
|
||
},
|
||
],
|
||
},
|
||
),
|
||
CompareScenario(
|
||
id="multi_layer_mix",
|
||
name="多图层混合",
|
||
description="main + broll + overlay + audio 四图层",
|
||
priority="P1",
|
||
plan_payload={
|
||
"width": 1280,
|
||
"height": 720,
|
||
"fps": 25,
|
||
"clips": [
|
||
{
|
||
"clip_type": "main",
|
||
"asset_id": "sample_5s.mp4",
|
||
"duration": 4.0,
|
||
"order": 0,
|
||
"transition_effect": "fade",
|
||
},
|
||
{
|
||
"clip_type": "main",
|
||
"asset_id": "sample_5s.mp4",
|
||
"duration": 4.0,
|
||
"order": 1,
|
||
"transition_effect": "slideup",
|
||
},
|
||
{"clip_type": "broll", "asset_id": "sample_broll.mp4", "duration": 8.0, "order": 0},
|
||
{"clip_type": "overlay", "asset_id": "sample_overlay.png", "duration": 8.0, "order": 0},
|
||
{
|
||
"clip_type": "main",
|
||
"asset_id": "sample_bgm.mp3",
|
||
"duration": 8.0,
|
||
"order": 0,
|
||
"config": {"role": "audio", "volume": 0.3},
|
||
},
|
||
],
|
||
},
|
||
),
|
||
CompareScenario(
|
||
id="image_background",
|
||
name="图片背景",
|
||
description="background图片层 + 主视频,验证背景层无音频",
|
||
priority="P1",
|
||
plan_payload={
|
||
"width": 1280,
|
||
"height": 720,
|
||
"fps": 25,
|
||
"clips": [
|
||
{"clip_type": "background", "asset_id": "sample_bg.jpg", "duration": 5.0, "order": 0},
|
||
{"clip_type": "main", "asset_id": "sample_5s.mp4", "duration": 5.0, "order": 0},
|
||
],
|
||
},
|
||
),
|
||
CompareScenario(
|
||
id="no_audio_video",
|
||
name="无音轨视频",
|
||
description="源视频无音频流,验证无音轨防御逻辑",
|
||
priority="P0",
|
||
plan_payload={
|
||
"width": 1280,
|
||
"height": 720,
|
||
"fps": 25,
|
||
"clips": [
|
||
{"clip_type": "main", "asset_id": "sample_silent_5s.mp4", "duration": 5.0, "order": 0},
|
||
],
|
||
},
|
||
),
|
||
CompareScenario(
|
||
id="long_video_stress",
|
||
name="长视频压力",
|
||
description="10个clip + 多种转场,性能压力测试",
|
||
priority="P2",
|
||
plan_payload={
|
||
"width": 1280,
|
||
"height": 720,
|
||
"fps": 25,
|
||
"clips": [
|
||
{
|
||
"clip_type": "main",
|
||
"asset_id": "sample_5s.mp4",
|
||
"duration": 3.0,
|
||
"order": i,
|
||
"transition_effect": ["cut", "fade", "slideleft", "slidedown", "dissolve"][i % 5],
|
||
}
|
||
for i in range(10)
|
||
],
|
||
},
|
||
),
|
||
CompareScenario(
|
||
id="vertical_portrait",
|
||
name="竖屏9:16",
|
||
description="竖屏分辨率,验证scale策略(铺满裁剪)",
|
||
priority="P2",
|
||
plan_payload={
|
||
"width": 720,
|
||
"height": 1280,
|
||
"fps": 25,
|
||
"clips": [
|
||
{"clip_type": "main", "asset_id": "sample_5s.mp4", "duration": 5.0, "order": 0},
|
||
],
|
||
},
|
||
),
|
||
]
|
||
|
||
|
||
def get_scenarios_by_priority(min_priority: str = "P2") -> list[CompareScenario]:
|
||
"""按优先级过滤场景.
|
||
|
||
P0 包含 P0
|
||
P1 包含 P0 + P1
|
||
P2 包含全部
|
||
"""
|
||
priority_order = {"P0": 0, "P1": 1, "P2": 2}
|
||
threshold = priority_order.get(min_priority, 2)
|
||
return [s for s in SCENARIOS if priority_order.get(s.priority, 2) <= threshold]
|