在使用pytest进行测试时,我们经常需要针对不同的输入值执行相同的测试逻辑。为了提高测试效率,避免重复编写相似的测试用例,pytest提供了参数化测试的功能。这一功能允许我们轻松执行同一测试用例的多个变体,从而覆盖更多的测试场景。
一、基本用法
pytest的参数化测试主要通过@pytest.mark.parametrize
装饰器实现。该装饰器接收两个参数:第一个是字符串,表示参数的名称;第二个是参数的值列表,每个值都会作为一次独立的测试执行。
python
import pytest
@pytest.mark.parametrize("input,expected", [
(1, 2),
(2, 3),
(3, 4)
])
def test_increment(input, expected):
assert input + 1 == expected
|---|
| |
在这个例子中,test_increment
函数会被执行三次,每次都会使用parametrize
装饰器中定义的一组参数。
二、高级用法
除了基本用法外,pytest的参数化测试还支持一些高级功能,如使用ids
为测试用例设置别名、使用indirect
参数进行间接参数化等。
使用ids
设置别名
ids
参数允许我们为每个测试用例设置一个别名,这样在运行测试时,pytest会显示这些别名而不是参数的默认值。
python
import pytest
@pytest.mark.parametrize("input,expected", [
pytest.param(1, 2, marks=pytest.mark.basic),
pytest.param(2, 3, marks=pytest.mark.basic, id="basic_2"),
pytest.param(3, 4, id="basic_3"),
])
def test_increment(input, expected):
assert input + 1 == expected
|---|
| |
在这个例子中,第二个和第三个测试用例分别使用了id
参数来设置别名。
使用indirect
进行间接参数化
indirect
参数允许我们将参数传递给fixture函数,而不是直接传递给测试用例函数。这可以用于更复杂的测试场景,其中fixture函数需要根据不同的参数来设置测试环境。
python
import pytest
@pytest.fixture
def my_fixture(request):
param = request.param
return param
@pytest.mark.parametrize("my_fixture", [1, 2, 3], indirect=True)
def test_with_fixture(my_fixture):
assert my_fixture > 0
|---|
| |
在这个例子中,my_fixture
是一个fixture函数,它接收一个参数并返回该参数。test_with_fixture
函数使用@pytest.mark.parametrize
装饰器进行参数化,并通过indirect=True
告诉pytest将参数传递给fixture函数。