235 lines
8.6 KiB
Python
235 lines
8.6 KiB
Python
#!/usr/bin/env python3
|
|
"""
|
|
快速测试视频切分功能
|
|
"""
|
|
|
|
import os
|
|
import sys
|
|
import tempfile
|
|
import shutil
|
|
from pathlib import Path
|
|
|
|
# 添加项目根目录到Python路径
|
|
project_root = Path(__file__).parent.parent
|
|
sys.path.insert(0, str(project_root))
|
|
|
|
def test_video_splitting():
|
|
"""测试视频切分功能"""
|
|
print("🎬 视频切分功能测试")
|
|
print("=" * 50)
|
|
|
|
# 查找测试视频
|
|
assets_dir = project_root / "assets"
|
|
video_files = list(assets_dir.rglob("*.mp4"))
|
|
|
|
if not video_files:
|
|
print("❌ 没有找到测试视频文件")
|
|
return False
|
|
|
|
# 选择第一个视频文件进行测试
|
|
test_video = video_files[0]
|
|
print(f"📹 使用测试视频: {test_video}")
|
|
print(f" 文件大小: {test_video.stat().st_size / (1024*1024):.1f} MB")
|
|
|
|
# 创建临时目录
|
|
temp_dir = tempfile.mkdtemp(prefix="video_test_")
|
|
print(f"📁 临时目录: {temp_dir}")
|
|
|
|
try:
|
|
# 设置临时目录
|
|
from unittest.mock import patch
|
|
|
|
with patch('python_core.config.settings') as mock_settings:
|
|
mock_settings.temp_dir = Path(temp_dir)
|
|
|
|
# 导入MediaManager
|
|
from python_core.services.media_manager import MediaManager
|
|
|
|
print("\n🔧 初始化MediaManager...")
|
|
media_manager = MediaManager()
|
|
|
|
print("✅ MediaManager初始化成功")
|
|
|
|
# 测试依赖可用性
|
|
print("\n🔍 检查依赖...")
|
|
opencv_available = media_manager.dependency_manager.is_available('opencv')
|
|
scenedetect_available = media_manager.dependency_manager.is_available('scenedetect')
|
|
|
|
print(f" OpenCV: {'✅' if opencv_available else '❌'}")
|
|
print(f" PySceneDetect: {'✅' if scenedetect_available else '❌'}")
|
|
|
|
if not opencv_available and not scenedetect_available:
|
|
print("❌ 没有可用的视频处理库")
|
|
return False
|
|
|
|
# 测试视频信息提取
|
|
print("\n📊 提取视频信息...")
|
|
try:
|
|
video_info = media_manager._get_video_info(str(test_video))
|
|
print(f" 时长: {video_info.get('duration', 0):.2f}秒")
|
|
print(f" 分辨率: {video_info.get('width', 0)}x{video_info.get('height', 0)}")
|
|
print(f" 帧率: {video_info.get('fps', 0):.2f} FPS")
|
|
print(f" 文件大小: {video_info.get('file_size', 0) / (1024*1024):.1f} MB")
|
|
except Exception as e:
|
|
print(f"❌ 视频信息提取失败: {e}")
|
|
return False
|
|
|
|
# 测试场景检测
|
|
print("\n🎯 检测场景变化...")
|
|
try:
|
|
scene_changes = media_manager._detect_scene_changes(str(test_video), threshold=30.0)
|
|
print(f" 检测到 {len(scene_changes)} 个场景变化点")
|
|
print(f" 场景时间点: {[f'{t:.2f}s' for t in scene_changes[:5]]}")
|
|
if len(scene_changes) > 5:
|
|
print(f" ... 还有 {len(scene_changes) - 5} 个")
|
|
except Exception as e:
|
|
print(f"❌ 场景检测失败: {e}")
|
|
# 使用手动场景变化点
|
|
duration = video_info.get('duration', 10.0)
|
|
scene_changes = [0.0, duration / 2, duration]
|
|
print(f" 使用手动场景变化点: {scene_changes}")
|
|
|
|
# 测试视频切分
|
|
print("\n✂️ 执行视频切分...")
|
|
try:
|
|
segments = media_manager._split_video_by_scenes(
|
|
str(test_video),
|
|
scene_changes,
|
|
"test_video_001",
|
|
["测试", "自动分镜"]
|
|
)
|
|
|
|
print(f"✅ 成功创建 {len(segments)} 个视频片段")
|
|
|
|
# 检查片段详情
|
|
total_duration = 0
|
|
for i, segment in enumerate(segments):
|
|
# 处理字典格式的segment
|
|
if isinstance(segment, dict):
|
|
filename = segment.get('filename', f'segment_{i}')
|
|
duration = segment.get('duration', 0)
|
|
start_time = segment.get('start_time', 0)
|
|
end_time = segment.get('end_time', 0)
|
|
file_path = segment.get('file_path', '')
|
|
else:
|
|
# 处理对象格式的segment
|
|
filename = segment.filename
|
|
duration = segment.duration
|
|
start_time = segment.start_time
|
|
end_time = segment.end_time
|
|
file_path = segment.file_path
|
|
|
|
print(f" 片段 {i+1}: {filename}")
|
|
print(f" 时长: {duration:.2f}秒")
|
|
print(f" 时间范围: {start_time:.2f}s - {end_time:.2f}s")
|
|
|
|
# 检查文件是否存在
|
|
if file_path:
|
|
segment_path = Path(file_path)
|
|
if segment_path.exists():
|
|
size_mb = segment_path.stat().st_size / (1024 * 1024)
|
|
print(f" 文件大小: {size_mb:.1f} MB")
|
|
print(f" 文件路径: {segment_path}")
|
|
else:
|
|
print(f" ⚠️ 文件不存在: {file_path}")
|
|
|
|
total_duration += duration
|
|
print()
|
|
|
|
print(f"📊 切分统计:")
|
|
print(f" 原视频时长: {video_info.get('duration', 0):.2f}秒")
|
|
print(f" 片段总时长: {total_duration:.2f}秒")
|
|
print(f" 时长差异: {abs(video_info.get('duration', 0) - total_duration):.2f}秒")
|
|
|
|
return True
|
|
|
|
except Exception as e:
|
|
print(f"❌ 视频切分失败: {e}")
|
|
import traceback
|
|
traceback.print_exc()
|
|
return False
|
|
|
|
finally:
|
|
# 清理临时目录
|
|
print(f"\n🧹 清理临时目录: {temp_dir}")
|
|
shutil.rmtree(temp_dir, ignore_errors=True)
|
|
|
|
def test_multiple_videos():
|
|
"""测试多个视频文件"""
|
|
print("\n" + "=" * 50)
|
|
print("🎬 多视频测试")
|
|
print("=" * 50)
|
|
|
|
assets_dir = project_root / "assets"
|
|
video_files = list(assets_dir.rglob("*.mp4"))[:3] # 只测试前3个
|
|
|
|
success_count = 0
|
|
|
|
for i, video_file in enumerate(video_files, 1):
|
|
print(f"\n📹 测试视频 {i}/{len(video_files)}: {video_file.name}")
|
|
|
|
try:
|
|
# 简单的信息提取测试
|
|
from python_core.services.media_manager import MediaManager
|
|
media_manager = MediaManager()
|
|
|
|
video_info = media_manager._get_video_info(str(video_file))
|
|
scene_changes = media_manager._detect_scene_changes(str(video_file))
|
|
|
|
print(f" ✅ 时长: {video_info.get('duration', 0):.2f}秒")
|
|
print(f" ✅ 场景变化: {len(scene_changes)} 个")
|
|
|
|
success_count += 1
|
|
|
|
except Exception as e:
|
|
print(f" ❌ 处理失败: {e}")
|
|
|
|
print(f"\n📊 多视频测试结果: {success_count}/{len(video_files)} 成功")
|
|
return success_count == len(video_files)
|
|
|
|
def main():
|
|
"""主函数"""
|
|
print("🚀 开始视频切分测试")
|
|
|
|
# 检查环境
|
|
print(f"Python版本: {sys.version}")
|
|
print(f"项目目录: {project_root}")
|
|
|
|
# 检查assets目录
|
|
assets_dir = project_root / "assets"
|
|
if not assets_dir.exists():
|
|
print("❌ assets目录不存在")
|
|
return 1
|
|
|
|
video_files = list(assets_dir.rglob("*.mp4"))
|
|
if not video_files:
|
|
print("❌ 没有找到视频文件")
|
|
return 1
|
|
|
|
print(f"📹 找到 {len(video_files)} 个视频文件")
|
|
|
|
# 运行测试
|
|
try:
|
|
# 单视频详细测试
|
|
success1 = test_video_splitting()
|
|
|
|
# 多视频快速测试
|
|
success2 = test_multiple_videos()
|
|
|
|
if success1 and success2:
|
|
print("\n🎉 所有测试通过!")
|
|
return 0
|
|
else:
|
|
print("\n⚠️ 部分测试失败")
|
|
return 1
|
|
|
|
except Exception as e:
|
|
print(f"\n❌ 测试过程中出错: {e}")
|
|
import traceback
|
|
traceback.print_exc()
|
|
return 1
|
|
|
|
if __name__ == "__main__":
|
|
exit_code = main()
|
|
sys.exit(exit_code)
|