参数化测试
基础 @pytest.mark.parametrize
import pytest
# 单个参数
@pytest.mark.parametrize("n,expected", [
(1, 1),
(5, 120),
(10, 3628800),
])
def test_factorial(n, expected):
assert factorial(n) == expected
# 多个参数 — 元组形式
@pytest.mark.parametrize("input_str,expected", [
("hello", "HELLO"),
("World", "WORLD"),
("", ""),
])
def test_to_upper(input_str, expected):
assert input_str.upper() == expected
ids — 自定义测试名称
import pytest
# 显式字符串 IDs
@pytest.mark.parametrize("value,expected", [
(0, True),
(1, False),
(-1, False),
], ids=["零", "正数", "负数"])
def test_is_zero(value, expected):
assert (value == 0) == expected
# pytest.param 携带元数据
@pytest.mark.parametrize("config", [
pytest.param({"debug": True}, id="调试模式"),
pytest.param({"debug": False}, id="生产模式"),
])
indirect — 通过 Fixtures 传参
import pytest
@pytest.fixture
def user_factory(request):
role = request.param
return create_user(role=role, name=f"{role}_用户")
@pytest.mark.parametrize("user_factory", ["admin", "editor", "viewer"],
indirect=True)
def test_user_dashboard(user_factory):
user = user_factory
response = client.get("/dashboard", user=user)
assert response.status_code == 200
矩阵测试 — 叠加 parametrize
import pytest
# 叠加产生笛卡尔积(2x3 = 6 个测试用例)
@pytest.mark.parametrize("browser", ["chrome", "firefox"])
@pytest.mark.parametrize("resolution", ["1920x1080", "1366x768", "375x812"])
def test_layout(browser, resolution):
driver = setup_driver(browser, resolution)
assert driver.page_renders_correctly()
parametrize 与 Fixtures 结合
import pytest
@pytest.fixture
def api_client(app):
return app.test_client()
@pytest.mark.parametrize("endpoint,expected_status", [
("/health", 200),
("/api/v1/users", 200),
("/nonexistent", 404),
])
def test_endpoints(api_client, auth_headers, endpoint, expected_status):
response = api_client.get(endpoint, headers=auth_headers)
assert response.status_code == expected_status
parametrize 与标记组合
| 标记 | 用法 | 效果 |
|---|---|---|
marks=pytest.mark.skip | 跳过特定用例 | 无条件跳过 |
pytest.mark.skipif | 条件跳过 | 根据条件决定是否跳过 |
marks=pytest.mark.xfail | 预期失败 | 失败视为通过 |
pytest.mark.slow | 自定义标记 | 用 -m slow 选择执行 |