使用会话范围和autouse = True在夹具中定义对象的最佳方法是什么,所以它可用于所有测试?
@pytest.fixture(scope='session', autouse=True)
def setup_func(request):
obj = SomeObj()
接下来,我想要一些先前创建的魔法obj
将出现在每个测试上下文中,而不需要每个测试来定义setup_func
fixture。
def test_one():
obj.do_something_fancy()
答案 0 :(得分:6)
我的建议是将夹具添加到conftest.py
并确保从夹具中返回要生成的对象。
如上所述,这使得" autouse"有点没用。
在测试的根目录中,将fixture添加到名为conftest.py
的文件:
@pytest.fixture(scope='session', autouse=True)
def someobj(request):
return SomeObj()
根文件下的任何测试文件都可以访问此fixture(例如test_foo.py
):
def test_foo(someobj):
assert isinstance(someobj, SomeObj)
另一种方法是使用在同一测试中定义的或从模块导入的全局变量。
例如conftest.py
:
someobj = None
@pytest.fixture(scope='session', autouse=True)
def prep_someobj(request):
someobj = SomeObj()
然后在你的测试中:
from . import conftest
def test_foo():
assert isinstance(conftest.someobj, SomeObj)
在我看来,这比第一种方法更不易读,也更麻烦。
答案 1 :(得分:2)
一个更通用的模式是在比赛结束时返回locals()
,您将可以轻松引用在灯具中创建的任何内容。
conftest.py
@pytest.fixture(scope='session')
def setup_func(request):
obj1 = SomeObj()
obj2 = SomeObj()
return locals()
test_stuff.py
def test_one(setup_func):
setup_func['obj1'].do_something_fancy()
def test_two(setup_func):
setup_func['obj2'].do_something_fancy()
答案 2 :(得分:0)
Another possibility is to wrap your tests in a class and use class variables to only define the object instance once. This assumes you are able to wrap all tests in a single class and so this answer may address a less general, but similar use case. For example,
class SomeObj():
"""This object definition may exist in another module and be imported."""
def __init__(self):
self.x = 5
def do_something_fancy(self, y):
return self.x * y
class TestX():
# Object instance to share across tests
someobj = SomeObj()
def test_x(self):
assert TestX.someobj.x == 5
def test_fancy(self):
fancy_factor = 10
result = TestX.someobj.do_something_fancy(fancy_factor)
assert result == 50