Okay, the scenario is very simple. I have this file structure:
.
├── interface.py
├── pkg
│ ├── __init__.py
│ ├── mod1.py
│ ├── mod2.py
Now, these are my conditions:
- mod2 needs to import mod1.
- both interface.py and mod2 needs to be run independently as a main script. If you want, think interface as the actual program and mod2 as an internal tester of the package.
So, in Python 2 I would simply do import mod1
inside mod2.py and both python2 mod2.py
and python2 interface.py
would work as expected.
However, and this is the part I less understand, using Python 3.5.2, if I do import mod1
; then I can do python3 mod2.py
, but python3 interface.py
throws: ImportError: No module named 'mod1'
:(
So, apparently, python 3 proposes to use import pkg.mod1
to avoid collisions against built-in modules. Ok, If I use that I can do python3 interface.py
; but then I can't python3 mod2.py
because: ImportError: No module named 'pkg'
Similarly, If I use relative import:
from . import mod1
then python3 interface.py
works; but mod2.py says SystemError: Parent module '' not loaded, cannot perform relative import
:( :(
The only "solution", I've found is to go up one folder and do python -m pkg.mod2
and then it works. But do we have to be adding the package prefix pkg
to every import to other modules within that package? Even more, to run any scripts inside the package, do I have to remember to go one folder up and use the -m switch? That's the only way to go??
I'm confused. This scenario was pretty straightforward with python 2, but looks awkward in python 3.
UPDATE: I have upload those files with the (referred as "solution" above) working source code here: https://gitlab.com/Akronix/test_python3_packages. Note that I still don't like it, and looks much uglier than the python2 solution.
Related SO questions I've already read:
- Python -- import the package in a module that is inside the same package
- How to do relative imports in Python?
- Absolute import module in same package
Related links:
from pkg.mod1 import fun
, you could use a relative import, such asfrom .mod1 import fun
, orfrom . import mod1
which would alleviate the need to mention the name of the package. Those work in python2 and 3. Good readup here, relative imports for the billionth time – Lavettelavigne