Files
InterfaceAutoTest/conftest.py
CNWei d05757f7cc feat(core): 增强 Exchange,实现智能变量替换与类型保持
- 优化 conftest.py 增加异常日志记录和测试报告环境信息
 - 其他优化
2026-03-16 19:15:01 +08:00

140 lines
4.8 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#!/usr/bin/env python
# coding=utf-8
"""
@desc: Pytest 配置文件,用于设置全局 Fixture 和钩子函数
"""
import platform
from typing import Any
import pytest
from pathlib import Path
import logging
from core.context import VariableStore, ExecutionEnv
from core.session import Session
from core.exchange import Exchange
from core.settings import EXTRACT_CACHE,base_url
logger = logging.getLogger(__name__)
# 注册命令行参数
def pytest_addoption(parser: Any) -> None:
"""
注册自定义命令行参数。
允许用户通过命令行传递参数来控制测试执行的行为。
Args:
parser: Pytest 的命令行参数解析器对象。
"""
parser.addoption("--test_dir", action="store", default=None, help="测试用例目录")
parser.addoption("--env", action="store", default="test", help="运行环境标识 (test/prod/dev)")
@pytest.fixture(scope="session")
def execution_context():
"""
[Session级别 Fixture] 全局执行上下文环境。
职责:
1. 生命周期管理:初始化并管理全局唯一的 Session、变量存储 (Store) 和 变量交换器 (Exchanger)。
2. 资源复用:确保 HTTP 连接池复用,减少握手开销。
3. 数据持久化:在测试结束时自动将提取的变量回写到磁盘。
Yields:
ExecutionEnv: 包含 session, store, exchanger 的环境对象实例。
"""
# Setup: 加载环境
store = VariableStore(EXTRACT_CACHE)
exchanger = Exchange(variable_cache=store.store)
session = Session(base_url)
env = ExecutionEnv(session, store, exchanger)
yield env # 注入到测试用例中
# Teardown: 统一持久化与清理
store.persist()
session.close()
def pytest_exception_interact(node: Any, call: Any, report: Any) -> None:
"""
[Hook] 异常交互钩子。
当测试用例执行失败(断言错误或代码异常)时触发。
主要用于捕获详细的错误堆栈信息,并将其格式化输出到日志中,
以便于在控制台或日志文件中快速定位问题。
Args:
node: 发生异常的测试节点Item 或 Collector
call: 测试调用信息(包含 excinfo 异常信息)。
report: 测试报告对象。
"""
if report.failed:
# 获取详细的错误堆栈(包含 assert 的对比信息)
# long,short,no-locals
exc_info = call.excinfo.getrepr(style='short')
logger.error(f"\n{'=' * 40} TEST FAILED {'=' * 40}\n"
f"Node: {node.name}\n"
f"Error:\n{exc_info}"
)
logger.error("=" * 93 + "\n")
def pytest_sessionfinish(session: Any, exitstatus: int) -> None:
"""
[Hook] 会话结束钩子。
在所有测试执行完毕后调用。主要完成以下工作:
1. 根据退出状态码记录不同级别的日志信息。
2. 收集测试环境信息(如 Base URL, Python 版本, 操作系统等)。
3. 生成 `environment.properties` 文件供 Allure 报告展示。
Args:
session: Pytest 会话对象。
exitstatus: 整体测试执行的退出状态码。
"""
match exitstatus:
case pytest.ExitCode.OK:
logging.info("测试全部通过!")
case pytest.ExitCode.TESTS_FAILED:
logging.warning("部分测试用例执行失败,请检查报告。")
case pytest.ExitCode.INTERRUPTED:
logging.error("测试被用户手动中断Ctrl+C")
case pytest.ExitCode.INTERNAL_ERROR:
logging.critical("Pytest 发生内部错误!")
case pytest.ExitCode.USAGE_ERROR:
logging.error("Pytest 命令行参数错误或用法不当。")
case pytest.ExitCode.NO_TESTS_COLLECTED:
logging.warning("未发现任何测试用例。")
case _:
logging.error(f"未知错误状态码: {exitstatus}")
report_dir = session.config.getoption("--alluredir")
if not report_dir:
return
report_path = Path(report_dir)
# 收集环境信息 (适配接口自动化)
env_info = {
"Base URL": base_url,
"Environment": session.config.getoption("--env"),
"Python Version": platform.python_version(),
"OS System": platform.system(),
"Project": "Interface Auto Test"
}
try:
if not report_path.exists():
report_path.mkdir(parents=True, exist_ok=True)
# 生成 environment.properties 文件
env_file = report_path / "environment.properties"
with env_file.open("w", encoding="utf-8") as f:
for k, v in env_info.items():
f.write(f"{k}={v}\n")
logging.info("Allure 环境信息已生成。")
except Exception as e:
logging.error(f"无法写入环境属性: {e}")