DazedAndConfused
DazedAndConfused

Reputation: 21

Python application works when installed via pip but not when running directly

I need help setting up my directory structure for a python application. It is a command line application (using Click, if that matters).

My directory structure looks like this:

mycli
├── mycli
│   ├── cli.py
│   ├── __init__.py
│   └── mycli.py
└── setup.py

In mycli/mycli/__init__.py I have one line of code:

__application__ = "my-cli"

In mycli/mycli/cli.py I have this:

from mycli import __application__
import click
import sys

@click.group()
def my_cli():
    """ rest of my code """

if __name__ == "__main__":
    sys.exit(my_cli())

Finally, in my setup.py, I have added an entry point so that I can use this application on the command line:

entry_points={
    'console_scripts': [
        'my-cli=mycli.cli:my_cli',
    ],
},

I can install my application using pip install -e . and then execute my-cli as expected. This works.

The problem I am having is that I want to run python mycli/cli.py as well. This is useful for debugging purposes. It fails to read the __application__ though:

$ python mycli/cli.py 
Traceback (most recent call last):
  File "mycli/cli.py", line 1, in <module>
    from mycli import __application__
ImportError: cannot import name '__application__'

What do I need to do with my project layout so that I can continue to use the entry_points in setup.py AND be able to run my application with python mycli/cli.py?

I tried to change the import to

from .mycli import __application__

But I receive these errors:

When running python mycli/cli.py

ModuleNotFoundError: No module named '__main__.mycli'; __main__ is not a package

The entry_point breaks with:

ImportError: cannot import name '__application__'

Upvotes: 2

Views: 248

Answers (1)

Stephen Rauch
Stephen Rauch

Reputation: 49814

Your problem is a conflicting namespace. Your program has the same name as your module. So:

from mycli import __application__ 

tries to import from mycli.py, not from mycli/__init__.py. I suggest you rename your script to my-cli.py.

Upvotes: 2

Related Questions