__init__.py code called twice and its significance with package import

2.4k views Asked by At

I have a simple python project fro learning with two files __init__.py and __main__.py When I executed python -m pkg_name it runs both __init__.py and __main__.py

When I execute python -m pkg_name.__init__.py it invokes __init__.py twice.

I want to know why __init__.py is called twice when i call __init__.py Is it like the static code in java where when we call the class all the data in static code is automatically triggered.

What is the relevance of __init__.py in python and benefits of it getting executed when package is imported/loaded or called for processing. Please help me understand the concepts better.

"""Run a sequence of programs, testing python code __main__ variable

Each program (except the first) receives standard output of the
previous program on its standard input, by default. There are several
alternate ways of passing data between programs.

"""

def _launch():
    print('Pipeline Launched')


if __name__ == '__main__':
    print('This module is running as the main module!')
    _launch()
> __init__.py

"""This is the __init__.py file of pipleline package

Used for testing the import statements.


"""

print(__name__)
print('This is the __init__.py file of pipleline package')
print('Exiting __init__ of pipeline package after all initialization')
2

There are 2 answers

3
Prajwal On

It is used to define a folder as a package, which contains required modules and resources.

You can use is as an empty file or add docs about the package or setup initial conditions for the module.

Please checkout the python documentation.

Also, as mentioned by Natecat, __init__.py gets executed whenever you load a package. That's why when you explicitly call __init__.py, it loads the package (1st load) then executes __init__.py (2nd load).

0
Laurent LAPORTE On

The following command is used to execute a Python module or package:

python -m module

Where module is the name of the module/package without .py extension.

  • if the name matches a script, it is byte-compiled and executed,
  • if the name matches a directory with a __init__.py file and a __main__.py file, the directory is considered as being a Python package and is loaded first. Then the __main__.py script is executed.
  • if the name contains dots, e.g.: "mylib.mypkg.mymodule", Python browse each package and sub-package matching the dotted name and load it. Then it execute the last module (or last package which must contain a __main__.py file).

A (short) description is done in the official documentation: 29.4. main — Top-level script environment.

Your problem

If you run this command:

python -m pkg_name

It loads (and run) the __init__.py and __main__.py: this is the normal behavior.

If you run this command:

python -m pkg_name.__init__.py

It should fail if you leave the ".py" extension.

If it runs, the command loads the pkg_name package first: it execute the __init__.py first. Then it runs it again.