""" 统一测试工具接口标准 定义所有测试工具应遵循的统一接口规范 """ from abc import ABC, abstractmethod from typing import Dict, Any, List, Optional, Tuple from dataclasses import dataclass from enum import Enum class TestStatus(Enum): """测试状态枚举""" PASSED = "passed" FAILED = "failed" SKIPPED = "skipped" RUNNING = "running" class LogLevel(Enum): """日志级别枚举""" DEBUG = "DEBUG" INFO = "INFO" WARNING = "WARNING" ERROR = "ERROR" CRITICAL = "CRITICAL" @dataclass class TestConfig: """测试配置数据类""" name: str version: str description: str # API配置 api_base_url: str api_timeout: int api_max_retries: int # 认证配置 auth_enabled: bool auth_login_endpoint: str auth_username: str auth_password: str # 测试配置 test_parallel: bool test_retry_count: int # 报告配置 report_output_dir: str report_formats: List[str] report_include_details: bool # 日志配置 logging_level: str logging_file: str logging_console: bool @dataclass class TestResult: """测试结果数据类""" test_name: str test_type: str status: TestStatus url: str method: str status_code: int response_time: float error_message: str request_data: Dict[str, Any] response_data: Dict[str, Any] timestamp: str stack_trace: Optional[str] = None def to_dict(self) -> Dict[str, Any]: """转换为字典""" return { "test_name": self.test_name, "test_type": self.test_type, "status": self.status.value, "url": self.url, "method": self.method, "status_code": self.status_code, "response_time": self.response_time, "error_message": self.error_message, "request_data": self.request_data, "response_data": self.response_data, "timestamp": self.timestamp, "stack_trace": self.stack_trace } @dataclass class TestSummary: """测试摘要数据类""" total: int passed: int failed: int skipped: int pass_rate: float total_time: float start_time: str end_time: str def to_dict(self) -> Dict[str, Any]: """转换为字典""" return { "total": self.total, "passed": self.passed, "failed": self.failed, "skipped": self.skipped, "pass_rate": self.pass_rate, "total_time": self.total_time, "start_time": self.start_time, "end_time": self.end_time } @dataclass class ValidationRule: """验证规则数据类""" rule_type: str expected_value: Any path: Optional[str] = None description: Optional[str] = None class ITestTool(ABC): """测试工具接口""" @abstractmethod def get_name(self) -> str: """ 获取测试工具名称 Returns: 工具名称 """ pass @abstractmethod def get_version(self) -> str: """ 获取测试工具版本 Returns: 工具版本 """ pass @abstractmethod def load_config(self, config_path: str = None) -> None: """ 加载配置 Args: config_path: 配置文件路径 """ pass @abstractmethod def get_config(self) -> TestConfig: """ 获取配置 Returns: 配置对象 """ pass @abstractmethod def run_tests(self, test_cases: List[Any] = None) -> Tuple[List[TestResult], TestSummary]: """ 运行测试 Args: test_cases: 测试用例列表 Returns: (测试结果列表, 测试摘要) """ pass @abstractmethod def generate_report(self, results: List[TestResult], summary: TestSummary, format: str = "json") -> str: """ 生成测试报告 Args: results: 测试结果列表 summary: 测试摘要 format: 报告格式(json, html, pdf) Returns: 报告文件路径 """ pass @abstractmethod def set_log_level(self, level: LogLevel) -> None: """ 设置日志级别 Args: level: 日志级别 """ pass @abstractmethod def get_logs(self) -> List[str]: """ 获取日志 Returns: 日志列表 """ pass @abstractmethod def cleanup(self) -> None: """清理资源""" pass class IAPITester(ITestTool): """API测试工具接口""" @abstractmethod def login(self, username: str = None, password: str = None) -> bool: """ 用户登录 Args: username: 用户名 password: 密码 Returns: 是否登录成功 """ pass @abstractmethod def request( self, method: str, endpoint: str, data: Dict[str, Any] = None, params: Dict[str, Any] = None, headers: Dict[str, str] = None, expected_status: int = 200 ) -> TestResult: """ 发送HTTP请求 Args: method: HTTP方法 endpoint: API端点 data: 请求体数据 params: URL参数 headers: 请求头 expected_status: 期望的状态码 Returns: 测试结果 """ pass @abstractmethod def validate(self, result: TestResult, rules: List[ValidationRule]) -> TestResult: """ 验证测试结果 Args: result: 测试结果 rules: 验证规则列表 Returns: 验证后的测试结果 """ pass class IE2ETester(ITestTool): """E2E测试工具接口""" @abstractmethod def navigate(self, url: str) -> None: """ 导航到指定URL Args: url: 目标URL """ pass @abstractmethod def click(self, selector: str) -> None: """ 点击元素 Args: selector: 元素选择器 """ pass @abstractmethod def fill(self, selector: str, value: str) -> None: """ 填写表单字段 Args: selector: 元素选择器 value: 填充值 """ pass @abstractmethod def wait_for_element(self, selector: str, timeout: int = 5000) -> None: """ 等待元素出现 Args: selector: 元素选择器 timeout: 超时时间(毫秒) """ pass @abstractmethod def take_screenshot(self, name: str) -> str: """ 截取屏幕截图 Args: name: 截图名称 Returns: 截图文件路径 """ pass @abstractmethod def expect_visible(self, selector: str, timeout: int = 5000) -> None: """ 期望元素可见 Args: selector: 元素选择器 timeout: 超时时间(毫秒) """ pass @abstractmethod def expect_text(self, selector: str, expected_text: str, timeout: int = 5000) -> None: """ 期望元素包含指定文本 Args: selector: 元素选择器 expected_text: 期望的文本 timeout: 超时时间(毫秒) """ pass class IValidationEngine(ABC): """验证引擎接口""" @abstractmethod def validate_status_code(self, expected: int, actual: int) -> Tuple[bool, str]: """ 验证HTTP状态码 Args: expected: 期望的状态码 actual: 实际的状态码 Returns: (是否通过, 错误消息) """ pass @abstractmethod def validate_response_body(self, expected: Dict[str, Any], actual: Dict[str, Any]) -> Tuple[bool, str]: """ 验证响应体 Args: expected: 期望的响应体 actual: 实际的响应体 Returns: (是否通过, 错误消息) """ pass @abstractmethod def validate_contains(self, expected_value: Any, actual_value: Any) -> Tuple[bool, str]: """ 验证包含关系 Args: expected_value: 期望包含的值 actual_value: 实际的值 Returns: (是否通过, 错误消息) """ pass @abstractmethod def validate_equals(self, expected_value: Any, actual_value: Any) -> Tuple[bool, str]: """ 验证相等关系 Args: expected_value: 期望的值 actual_value: 实际的值 Returns: (是否通过, 错误消息) """ pass @abstractmethod def validate_json_path(self, path: str, expected_value: Any, actual_data: Dict[str, Any]) -> Tuple[bool, str]: """ 验证JSON路径 Args: path: JSON路径 expected_value: 期望的值 actual_data: 实际的数据 Returns: (是否通过, 错误消息) """ pass @abstractmethod def validate_regex(self, pattern: str, actual_value: str) -> Tuple[bool, str]: """ 验证正则表达式 Args: pattern: 正则表达式模式 actual_value: 实际的值 Returns: (是否通过, 错误消息) """ pass @abstractmethod def validate_header(self, expected_header: Dict[str, str], actual_headers: Dict[str, str]) -> Tuple[bool, str]: """ 验证响应头 Args: expected_header: 期望的响应头 actual_headers: 实际的响应头 Returns: (是否通过, 错误消息) """ pass @abstractmethod def validate_response_time(self, expected_max_time: float, actual_time: float) -> Tuple[bool, str]: """ 验证响应时间 Args: expected_max_time: 期望的最大响应时间(毫秒) actual_time: 实际的响应时间(毫秒) Returns: (是否通过, 错误消息) """ pass @abstractmethod def validate_schema(self, expected_schema: Dict[str, Any], actual_data: Dict[str, Any]) -> Tuple[bool, str]: """ 验证数据结构 Args: expected_schema: 期望的结构 actual_data: 实际的数据 Returns: (是否通过, 错误消息) """ pass class IReportGenerator(ABC): """报告生成器接口""" @abstractmethod def generate_json_report(self, results: List[TestResult], summary: TestSummary, filename: str = None) -> str: """ 生成JSON格式报告 Args: results: 测试结果列表 summary: 测试摘要 filename: 报告文件名 Returns: 报告文件路径 """ pass @abstractmethod def generate_html_report(self, results: List[TestResult], summary: TestSummary, filename: str = None) -> str: """ 生成HTML格式报告 Args: results: 测试结果列表 summary: 测试摘要 filename: 报告文件名 Returns: 报告文件路径 """ pass @abstractmethod def generate_pdf_report(self, results: List[TestResult], summary: TestSummary, filename: str = None) -> str: """ 生成PDF格式报告 Args: results: 测试结果列表 summary: 测试摘要 filename: 报告文件名 Returns: 报告文件路径 """ pass class ILogger(ABC): """日志记录器接口""" @abstractmethod def debug(self, message: str) -> None: """记录调试信息""" pass @abstractmethod def info(self, message: str) -> None: """记录信息""" pass @abstractmethod def warning(self, message: str) -> None: """记录警告""" pass @abstractmethod def error(self, message: str) -> None: """记录错误""" pass @abstractmethod def critical(self, message: str) -> None: """记录严重错误""" pass @abstractmethod def exception(self, message: str) -> None: """记录异常信息""" pass @abstractmethod def set_level(self, level: LogLevel) -> None: """ 设置日志级别 Args: level: 日志级别 """ pass @abstractmethod def get_logs(self) -> List[str]: """ 获取日志 Returns: 日志列表 """ pass class ITestDataGenerator(ABC): """测试数据生成器接口""" @abstractmethod def generate_user_data(self, overrides: Dict[str, Any] = None) -> Dict[str, Any]: """ 生成用户数据 Args: overrides: 覆盖的默认值 Returns: 用户数据 """ pass @abstractmethod def generate_role_data(self, overrides: Dict[str, Any] = None) -> Dict[str, Any]: """ 生成角色数据 Args: overrides: 覆盖的默认值 Returns: 角色数据 """ pass @abstractmethod def generate_menu_data(self, overrides: Dict[str, Any] = None) -> Dict[str, Any]: """ 生成菜单数据 Args: overrides: 覆盖的默认值 Returns: 菜单数据 """ pass @abstractmethod def generate_permission_data(self, overrides: Dict[str, Any] = None) -> Dict[str, Any]: """ 生成权限数据 Args: overrides: 覆盖的默认值 Returns: 权限数据 """ pass