Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

pytest-memray breaks anyio #119

Closed
godlygeek opened this issue Jun 12, 2024 · 6 comments · Fixed by #122
Closed

pytest-memray breaks anyio #119

godlygeek opened this issue Jun 12, 2024 · 6 comments · Fixed by #122

Comments

@godlygeek
Copy link
Contributor

Hola @pablogsal,

I am facing the same issue: the async tests are skipped if we pass --memray argument to pytest.

Steps to reproduce the issue:

Use the following test file: test_async.py

import pytest


@pytest.fixture
def anyio_backend():
    return 'asyncio'

@pytest.mark.anyio
async def test_async():
    assert True

Install required dependencies:

python -m pip install pytest anyio pytest-memray

The test runs as expected if --memray is not passed:

 python -m pytest -vv -x test_async.py

Output:

plugins: memray-1.6.0, anyio-4.0.0
collected 1 item                                                                                                                                                                                          

test_async.py::test_async PASSED

However, the test is skipped if we pass --memray:

 python -m pytest --memray -vv -x test_async.py

Output:

plugins: memray-1.6.0, anyio-4.0.0
collected 1 item                                                                                                                                                                                          

test_async.py::test_async SKIPPED (async def function and no async plugin installed (see warnings))                                                                                                 [100%]

============================================================================================ warnings summary =============================================================================================
test_async.py::test_async
  <MY_PROJECT_PATH>/.venv/lib/python3.9/site-packages/_pytest/python.py:151: PytestUnhandledCoroutineWarning: async def functions are not natively supported and have been skipped.
  You need to install a suitable plugin for your async framework, for example:
    - anyio
    - pytest-asyncio
    - pytest-tornasync
    - pytest-trio
    - pytest-twisted
    warnings.warn(PytestUnhandledCoroutineWarning(msg.format(nodeid)))

-- Docs: https://docs.pytest.org/en/stable/how-to/capture-warnings.html

Originally posted by @albertvillanova in #101 (comment)

@godlygeek
Copy link
Contributor Author

It looks anyio stores some state on the test function, and pytest-memray replaces the test function with a wrapper:

pyfuncitem.obj = wrapper
Those two things don't play nicely with each other.

@godlygeek
Copy link
Contributor Author

godlygeek commented Jun 12, 2024

Actually, looks like pytest is storing that state on the test function. anyio is just retrieving it.

We probably need to copy the test function's __dict__ over onto our wrapper.

@albertvillanova
Copy link

@godlygeek thanks for the investigation.

@godlygeek
Copy link
Contributor Author

My original analysis didn't spot the problem, actually. It's not that anyio isn't finding the state it expect on the wrapper, it's that anyio is completely ignoring the wrapper, because it only wants to process coroutine functions and ignore other stuff, and our wrapper isn't a coroutine function (even though calling it does return a coroutine, anyio is specifically looking only for async def functions).

We might be able to get around that by defining an async def wrapper if the function we're wrapping is an async def coroutine...

@godlygeek
Copy link
Contributor Author

This fix was released in pytest-memray 1.7.0

@albertvillanova
Copy link

Thanks!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants