I have made several Python packages, and I've always struggled to get imports to work. My normal project structure (as given in the Python packaging user guide) is as below:
packageName/
src/
packageName/
__init__.py
file1.py
file2.py
tests/
test_file1.py
test_file2.py
testData/
data_for_tests.py
At the moment, when I want to use a function from file2.py
in file1.py
, I do from .file2 import functionName
, but this seems very clunky and inelegant, and removes a lot of the benefits of abstracting things away behind files. I've also read lots of documentation saying that these relative imports are considered harmful.
I've tried just using import packageName.file2
, but when I run pytest it tells me that no such package exists. The only workaround I can think of is setting up a script to build it into a wheel and installing it locally first, but that doesn't seem particularly elegant. For reference, when I run pytest, I do it by running python3 -m pytest
from the package root directory.
In addition, when I want a function (say from file1
) to be usable as packageName.function
, I put from file1 import function
into the init file. This seems alright, but with all of this other stuff, I'm wondering if that's the right way to do it.
I work with a lot of engineers who use Python, but none of them are making packages to go on pip, and this seemed like the best place to come for an answer.
On the advice of Blue Robin, I tried just using from packageName import file2
, which worked on one file, but it didn't work when using other files (although I'm sure it's not a circular dependency issue). As a more concrete example, here is the project I'm currently working on:
countach/
src/
countach/
__init__.py
fileops.py | (no imports)
fixed.py | (no imports)
processing.py | (imports fileops and types)
types.py | (imports fixed)
I replaced the from .fileops import _function
to a from countach import fileops
, and it worked (removing the underscore from the given function). I then tried with other imports, and they didn't work, giving the error ImportError: cannot import name 'types' from 'countach'
(or the same type of error for fixed
). Googling these errors suggested that they normally occur in circular dependencies, but that can't be the case since fixed
doesn't import anything. I even tried doing it from the Python 3 REPL in the same directory, and it gave the same error.
I absolutely appreciate that you are giving your time for free here so I'm not expecting anyone to pore over anything, but any help would really be appreciated.
The code is available on my project's GitHub repository in tag v0.1.0N, but there is a further update. It turns out what was causing a lot of the problems is that I had a previous version of the package already installed via pip, so that was causing the ImportError
s to appear. I uninstalled the previous version, and now a different error has started to appear:
== types.py ==
from countach import fileops, types
Which gives the error:
ModuleNotFoundError: No module named 'countach'
I also tried replacing the from
-style imports with a direct import fileops
and import types
, but they also give corresponding ModuleNotFoundError
s. So I guess my question has changed a little into: with the directory structure as given above, how do I import other files from the same package? I can find lots of resources for importing from other directories, but the several files I have here make a lot more sense together than apart.