""" 日志记录器模块 提供结构化的测试日志记录功能。 """ import logging import sys from pathlib import Path from typing import Optional from datetime import datetime class TestLogger: """测试日志记录器""" def __init__(self, name: str = "e2e_test", log_dir: str = "logs"): self.name = name self.log_dir = Path(log_dir) self.log_dir.mkdir(parents=True, exist_ok=True) # 创建logger self.logger = logging.getLogger(name) self.logger.setLevel(logging.DEBUG) # 避免重复添加handler if not self.logger.handlers: # 控制台处理器 console_handler = logging.StreamHandler(sys.stdout) console_handler.setLevel(logging.INFO) console_formatter = logging.Formatter( "%(asctime)s - %(name)s - %(levelname)s - %(message)s", datefmt="%Y-%m-%d %H:%M:%S" ) console_handler.setFormatter(console_formatter) self.logger.addHandler(console_handler) # 文件处理器 log_file = self.log_dir / f"test_{datetime.now().strftime('%Y%m%d')}.log" file_handler = logging.FileHandler(log_file, encoding="utf-8") file_handler.setLevel(logging.DEBUG) file_formatter = logging.Formatter( "%(asctime)s - %(name)s - %(levelname)s - [%(filename)s:%(lineno)d] - %(message)s", datefmt="%Y-%m-%d %H:%M:%S" ) file_handler.setFormatter(file_formatter) self.logger.addHandler(file_handler) def debug(self, message: str) -> None: """记录调试日志""" self.logger.debug(message) def info(self, message: str) -> None: """记录信息日志""" self.logger.info(message) def warning(self, message: str) -> None: """记录警告日志""" self.logger.warning(message) def error(self, message: str, error: Optional[Exception] = None) -> None: """记录错误日志""" if error: self.logger.error(f"{message}: {str(error)}", exc_info=True) else: self.logger.error(message) def critical(self, message: str) -> None: """记录严重错误日志""" self.logger.critical(message) def start_test(self, test_name: str) -> None: """记录测试开始""" self.info(f"{'='*60}") self.info(f"开始执行测试: {test_name}") self.info(f"{'='*60}") def end_test(self, test_name: str, status: str, error: Optional[Exception] = None) -> None: """记录测试结束""" icon = "✅" if status == "passed" else "❌" self.info(f"{'='*60}") self.info(f"{icon} 测试结束: {test_name} - 状态: {status}") if error: self.error(f"错误信息: {str(error)}") self.info(f"{'='*60}") def start_step(self, step_name: str) -> None: """记录步骤开始""" self.info(f"▶️ 执行步骤: {step_name}") def end_step(self, step_name: str, status: str) -> None: """记录步骤结束""" icon = "✓" if status == "passed" else "✗" self.info(f"{icon} 步骤完成: {step_name} - 状态: {status}") # 全局日志记录器实例 _logger: Optional[TestLogger] = None def get_logger(name: str = "e2e_test", log_dir: str = "logs") -> TestLogger: """获取日志记录器实例""" global _logger if _logger is None: _logger = TestLogger(name, log_dir) return _logger