Skip to content

Commit 1db3ea9

Browse files
committed
Simplified fixture setup by relying on the fact that get_event_loop returns the loop provided by the event_loop fixture of pytest-asyncio.
1 parent 2b6f76b commit 1db3ea9

File tree

1 file changed

+22
-41
lines changed

1 file changed

+22
-41
lines changed

pytest_asyncio/plugin.py

+22-41
Original file line numberDiff line numberDiff line change
@@ -51,28 +51,35 @@ def pytest_pycollect_makeitem(collector, name, obj):
5151
@pytest.hookimpl(hookwrapper=True)
5252
def pytest_fixture_setup(fixturedef, request):
5353
"""Adjust the event loop policy when an event loop is produced."""
54+
if fixturedef.argname == "event_loop" and 'asyncio' in request.keywords:
55+
outcome = yield
56+
loop = outcome.get_result()
57+
policy = asyncio.get_event_loop_policy()
58+
try:
59+
old_loop = policy.get_event_loop()
60+
except RuntimeError as exc:
61+
if 'no current event loop' not in str(exc):
62+
raise
63+
old_loop = None
64+
policy.set_event_loop(loop)
65+
fixturedef.addfinalizer(lambda: policy.set_event_loop(old_loop))
66+
return
67+
5468
if isasyncgenfunction(fixturedef.func):
5569
# This is an async generator function. Wrap it accordingly.
56-
f = fixturedef.func
70+
generator = fixturedef.func
5771

58-
strip_event_loop = False
59-
if 'event_loop' not in fixturedef.argnames:
60-
fixturedef.argnames += ('event_loop', )
61-
strip_event_loop = True
6272
strip_request = False
6373
if 'request' not in fixturedef.argnames:
6474
fixturedef.argnames += ('request', )
6575
strip_request = True
6676

6777
def wrapper(*args, **kwargs):
68-
loop = kwargs['event_loop']
6978
request = kwargs['request']
70-
if strip_event_loop:
71-
del kwargs['event_loop']
7279
if strip_request:
7380
del kwargs['request']
7481

75-
gen_obj = f(*args, **kwargs)
82+
gen_obj = generator(*args, **kwargs)
7683

7784
async def setup():
7885
res = await gen_obj.__anext__()
@@ -89,50 +96,24 @@ async def async_finalizer():
8996
msg = "Async generator fixture didn't stop."
9097
msg += "Yield only once."
9198
raise ValueError(msg)
92-
93-
loop.run_until_complete(async_finalizer())
99+
asyncio.get_event_loop().run_until_complete(async_finalizer())
94100

95101
request.addfinalizer(finalizer)
96-
97-
return loop.run_until_complete(setup())
102+
return asyncio.get_event_loop().run_until_complete(setup())
98103

99104
fixturedef.func = wrapper
100-
101105
elif inspect.iscoroutinefunction(fixturedef.func):
102-
# Just a coroutine, not an async generator.
103-
f = fixturedef.func
104-
105-
strip_event_loop = False
106-
if 'event_loop' not in fixturedef.argnames:
107-
fixturedef.argnames += ('event_loop', )
108-
strip_event_loop = True
106+
coro = fixturedef.func
109107

110108
def wrapper(*args, **kwargs):
111-
loop = kwargs['event_loop']
112-
if strip_event_loop:
113-
del kwargs['event_loop']
114-
115109
async def setup():
116-
res = await f(*args, **kwargs)
110+
res = await coro(*args, **kwargs)
117111
return res
118112

119-
return loop.run_until_complete(setup())
113+
return asyncio.get_event_loop().run_until_complete(setup())
120114

121115
fixturedef.func = wrapper
122-
123-
outcome = yield
124-
125-
if fixturedef.argname == "event_loop" and 'asyncio' in request.keywords:
126-
loop = outcome.get_result()
127-
policy = asyncio.get_event_loop_policy()
128-
try:
129-
old_loop = policy.get_event_loop()
130-
except RuntimeError as exc:
131-
if 'no current event loop' not in str(exc):
132-
raise
133-
old_loop = None
134-
policy.set_event_loop(loop)
135-
fixturedef.addfinalizer(lambda: policy.set_event_loop(old_loop))
116+
yield
136117

137118

138119
@pytest.hookimpl(tryfirst=True, hookwrapper=True)

0 commit comments

Comments
 (0)