devsnd / cherrymusic

Stream your own music collection to all your devices! The easy to use free and open-source music streaming server.
http://www.fomori.org/cherrymusic
GNU General Public License v3.0
1.03k stars 189 forks source link

Can't install with pip #695

Closed pR0Ps closed 6 years ago

pR0Ps commented 6 years ago

Attempting to install in a clean virtual environment using pip fails with an error about cherrypy not being installed.

Expected

setup.py would install the required dependencies (including cherrypy).

Actual

(cherryvenv) [user@hostname ~]$ pip install cherrymusic
Collecting cherrymusic
  Downloading CherryMusic-0.40.0.tar.gz (802kB)
    100% |████████████████████████████████| 808kB 703kB/s 
    Complete output from command python setup.py egg_info:
    Traceback (most recent call last):
      File "<string>", line 1, in <module>
      File "/tmp/pip-build-rvq079vv/cherrymusic/setup.py", line 10, in <module>
        import cherrymusicserver
      File "/tmp/pip-build-rvq079vv/cherrymusic/cherrymusicserver/__init__.py", line 72, in <module>
        import cherrypy
    ModuleNotFoundError: No module named 'cherrypy'

    ----------------------------------------

Workaround

Install cherrypy manually using pip install cherrypy before installing cherrymusic

Environment

(probably not relevant but included for completeness's sake)

(cherryvenv) [user@hostname ~]$ python --version
Python 3.6.2
(cherryvenv) [user@hostname ~]$ pip --version
pip 9.0.1 from /home/user/cherryvenv/lib/python3.6/site-packages (python 3.6)
rjsberry commented 6 years ago

So from the traceback this is because cherrymusicserver/__init__.py imports cherrymusic, and setup.py imports cherrymusicserver.

https://github.com/devsnd/cherrymusic/blob/aa4eea153b96537383af336fccfb0cd9beee3ceb/cherrymusicserver/__init__.py#L72

https://github.com/devsnd/cherrymusic/blob/aa4eea153b96537383af336fccfb0cd9beee3ceb/setup.py#L10-L11

The cherrymusicserver and pathprovider imports in setup.py are just used to pull version/description info from the package itself. I see two potential solutions.

  1. The info from cherrymusicserver/__init__.py and cherrymusicserver/pathprovider.py could be moved to setup.py directly, omitting the above imports in setup.py altogether (based on the assumption that the cherrypy import in __init__.py cannot change).

  2. Encase the cherrypy import in __init__.py in a try/except block that catches the import error and mocks cherrypy if the import is from setup.py. Ugly hack of a solution but it could be made to work. Eg.

    try:
        import cherrypy
    except ImportError as err:
        if sys.argv[0] == 'setup.py':
            # Mock cherrypy here
        else:
            raise err

    This would fall apart if a cherrypy import crops up elsewhere in cherrymusicserver/__init__.py though (ie. another module imports cherrypy itself).

@devsnd I'd like to hear your input on this before working on a PR.

devsnd commented 6 years ago

Hey @pR0Ps, hey @rjsberry!

Thanks for your report and solution analysis!

I'd propose eliminate the imports in the setup.py (as Richard already suggested). To do so I think it would be best to duplicate the code of the pathprovider.sharedFolderName in the setup.py to resolve this issue: https://github.com/devsnd/cherrymusic/blob/aa4eea153b96537383af336fccfb0cd9beee3ceb/setup.py#L79

And for getting rid of the import of the cherrymusicserver we need to get the VERSION and DESCRIPTION variables from cherrymusicserver/__init__.py. I'd propose to go completely wild and parse the file manually to find the lines (and strings) that correspond to these variables.

Richard, would you take up that task? If you do it, I promise to release a new version right away 🤞