We welcome edits that make the post easier to understand and more valuable for readers. Because community members review edits, please try to make the post substantially better than how you found it, for example, by fixing grammar or adding additional resources and hyperlinks.
Required fields*
29
18
See python.org/dev/peps/pep-0366 -- "Note that this boilerplate is sufficient only if the top level package is already accessible via sys.path . Additional code that manipulates sys.path would be needed in order for direct execution to work without the top level package already being importable." -- this is the most disturbing bit to me since this "additional code" is actually quite long and can't be stored elsewhere in package to run easily.
I keep coming back to this post despite being a Python veteran. The main message for me is: Either fiddle around with sys.path and __package__ (which is rather ugly, see the other answers) or simply create a "main script" main.py in the root directory of your project and put all modules to be imported in subdirectories. main.py can then access all modules directly through their package names (= the names of the respective folders they're in).
This answer is currently off on a few important details regarding __name__ and sys.path. Specifically, with python -m pkg.mod, __name__ is set to __main__, not pkg.mod; relative imports are resolved using __package__ rather than __name__ in this case. Also, Python adds the script's directory rather than the current directory to sys.path when running python path/to/script.py; it adds the current directory to sys.path when running most other ways, including python -m pkg.mod.
Finally understand after hours of reading... Worth noting that code under if __name__ == '__main__' will still run when using -m. See the comment from @user2357112
A feature is broken if you have to spend an hour reading this, and if you have to google it time after time, and still only the gurus get it. The python designers dropped the ball on this one, and it should just work, the first time, like any other programming language.
A tag is a keyword or label that categorizes your question with other, similar questions. Choose one or more (up to 5) tags that will help answerers to find and interpret your question.
complete the sentence: my question is about...
use tags that describe things or concepts that are essential, not incidental to your question
sys.pathand__package__(which is rather ugly, see the other answers) or simply create a "main script"main.pyin the root directory of your project and put all modules to be imported in subdirectories.main.pycan then access all modules directly through their package names (= the names of the respective folders they're in).__name__andsys.path. Specifically, withpython -m pkg.mod,__name__is set to__main__, notpkg.mod; relative imports are resolved using__package__rather than__name__in this case. Also, Python adds the script's directory rather than the current directory tosys.pathwhen runningpython path/to/script.py; it adds the current directory tosys.pathwhen running most other ways, includingpython -m pkg.mod.if __name__ == '__main__'will still run when using -m. See the comment from @user2357112