131 lines
4.6 KiB
Python
131 lines
4.6 KiB
Python
# -*- coding: utf-8 -*-
|
|
"""RpaVideoSession 与 cmd_run 测试。"""
|
|
from __future__ import annotations
|
|
|
|
import io
|
|
import json
|
|
import os
|
|
import re
|
|
import unittest
|
|
from contextlib import redirect_stderr, redirect_stdout
|
|
from unittest.mock import AsyncMock, MagicMock, patch
|
|
|
|
from _support import IsolatedDataRoot, get_skill_root
|
|
|
|
from jiangchang_skill_core import config
|
|
|
|
|
|
class TestEnvExampleVideoDefaults(unittest.TestCase):
|
|
def test_env_example_contains_required_keys(self) -> None:
|
|
path = os.path.join(get_skill_root(), ".env.example")
|
|
with open(path, encoding="utf-8") as f:
|
|
text = f.read()
|
|
for key in (
|
|
"OPENCLAW_TEST_TARGET=mock",
|
|
"OPENCLAW_RECORD_VIDEO=1",
|
|
"OPENCLAW_ARTIFACTS_ON_FAILURE=1",
|
|
"OPENCLAW_BROWSER_HEADLESS=0",
|
|
"OPENCLAW_PLAYWRIGHT_STEALTH=1",
|
|
"AMAZON_SIM_REPORTS_URL=https://sandbox.jc2009.com",
|
|
):
|
|
self.assertIn(key, text, msg=f"missing {key!r} in .env.example")
|
|
|
|
|
|
class TestPrintVideoSummary(unittest.TestCase):
|
|
def test_cli_prints_video_path_when_enabled(self) -> None:
|
|
from service.task_run_support import _print_video_summary
|
|
|
|
buf = io.StringIO()
|
|
with redirect_stdout(buf), redirect_stderr(io.StringIO()):
|
|
_print_video_summary(
|
|
{
|
|
"enabled": True,
|
|
"path": r"D:\data\videos\download-settlement-report-amazon_demo.mp4",
|
|
"record_log_path": r"D:\data\logs\ffmpeg-record.log",
|
|
"warnings": [],
|
|
}
|
|
)
|
|
out = buf.getvalue()
|
|
self.assertIn("录屏路径", out)
|
|
self.assertIn("download-settlement-report-amazon_demo.mp4", out)
|
|
self.assertIn("录屏日志", out)
|
|
|
|
|
|
class TestCmdRunVideoSession(unittest.TestCase):
|
|
def test_cmd_run_creates_video_session_with_chinese_titles(self) -> None:
|
|
with IsolatedDataRoot(user_id="_video_run"):
|
|
os.environ["OPENCLAW_RECORD_VIDEO"] = "1"
|
|
os.environ["OPENCLAW_TEST_TARGET"] = "mock"
|
|
config.reset_cache()
|
|
|
|
from service import task_service
|
|
from service.amazon_report_adapter.base import DownloadSettlementResult
|
|
|
|
mock_result = DownloadSettlementResult(
|
|
ok=True,
|
|
job_id="MOCK-1",
|
|
file_path="/tmp/settlement.xlsx",
|
|
filename="settlement.xlsx",
|
|
date_from="2025-12-01",
|
|
date_to="2025-12-31",
|
|
)
|
|
|
|
mock_video = MagicMock()
|
|
mock_video.add_step = MagicMock()
|
|
mock_video.summary.return_value = {
|
|
"enabled": False,
|
|
"path": None,
|
|
"capture_path": None,
|
|
"record_log_path": None,
|
|
"warnings": [],
|
|
"voiceover_path": None,
|
|
"music_path": None,
|
|
"audio_warnings": [],
|
|
}
|
|
|
|
created: list[dict] = []
|
|
|
|
class _CapturingFakeSession:
|
|
def __init__(self, **kwargs):
|
|
created.append(kwargs)
|
|
|
|
async def __aenter__(self):
|
|
return mock_video
|
|
|
|
async def __aexit__(self, *args):
|
|
return None
|
|
|
|
mock_adapter = MagicMock()
|
|
mock_adapter.name = "mock"
|
|
mock_adapter.download_settlement.return_value = mock_result
|
|
|
|
with patch.object(task_service, "RpaVideoSession", _CapturingFakeSession):
|
|
with patch.object(task_service, "get_adapter", return_value=mock_adapter):
|
|
buf = io.StringIO()
|
|
with redirect_stdout(buf), redirect_stderr(io.StringIO()):
|
|
rc = task_service.cmd_run(
|
|
date_from="2025-12-01",
|
|
date_to="2025-12-31",
|
|
)
|
|
|
|
self.assertEqual(rc, 0)
|
|
self.assertTrue(created, "RpaVideoSession should be constructed")
|
|
kwargs = created[0]
|
|
self.assertEqual(kwargs.get("title"), "开始下载 Amazon 结算报表")
|
|
self.assertEqual(kwargs.get("closing_title"), "结算报表下载完成")
|
|
self.assertTrue(re.search(r"[\u4e00-\u9fff]", kwargs.get("title", "")))
|
|
|
|
out = buf.getvalue()
|
|
payload = json.loads(out.strip().splitlines()[-1])
|
|
self.assertTrue(payload.get("ok"))
|
|
|
|
from db import task_logs_repository as tlr
|
|
|
|
rows = tlr.list_task_logs(1)
|
|
self.assertTrue(rows)
|
|
self.assertEqual(rows[0][1], "download_settlement")
|
|
|
|
|
|
if __name__ == "__main__":
|
|
unittest.main()
|