__init__.py needed for imports to work in Pytest. But using Python 3.8

Tags: , ,



I have read that after Python 3.3, __init__.py is not required anymore, So I am not understanding why I need to add it (__init__.py) for my pytests to work.

Directory structure:

|- root/
   |- foo/
       |- bar.py
   |- tests/
       |- test_bar.py

In /foo/bar.py I have the following code

def five():
    return 5

In test_bar.py I have the following code

from foo import bar

test_bar():
    assert bar.five() == 5

I run the tests from /root like this:

/root$ pytest

If I place a __init__.py file in /tests, the test passes. Without it, I get the following error:

============ test session starts ============
platform darwin -- Python 3.8.0, pytest-6.1.2, py-1.9.0, pluggy-0.13.1
rootdir: /Users/my_user/my_folder/root
collected 0 items / 1 error     
______________ ERROR collecting tests/test_sorting.py ______________
ImportError while importing test module '/Users/my_user/my_folder/root/tests/test_bar.py'.
Hint: make sure your test modules/packages have valid Python names.
Traceback:
../../.pyenv/versions/3.8.0/lib/python3.8/importlib/__init__.py:127: in import_module
    return _bootstrap._gcd_import(name[level:], package, level)
tests/test_bar.py:1: in <module>
    from foo import bar
E   ModuleNotFoundError: No module named 'foo'

Answer

I’m not python expert but I think if you really don’t want to have __init__.py in every directory all you can do is create a sys.path for your root directory. This will allow you to import module inside root directory without __init__.py.

Find the site-packages folder (if u’re using venv then it’s inside your_env/lib/python3.x/site-packages) and inside site-packages folder create a .pth file and inside that file you can write the path to root directory. Example, /Users/your_name/Desktop/root. Now you can import like what you want.



Source: stackoverflow