setuptools: force version of another package (if p

2020-07-27 03:07发布

问题:

During development of Pylint, we encountered interesting problem related to non-dependency that may break pylint package.

Case is following:

  • python-future had a conflicting alias to configparser package. Quoting official docs:

    This release removes the configparser package as an alias for ConfigParser on Py2 to improve compatibility with Lukasz Langa’s backported configparser package. Previously python-future and the configparser backport clashed, causing various compatibility issues. (Issues #118, #181)

  • python-future itself is not a dependency of Pylint

What would be a standard way to enforce if python-future is present, force it to 0.16 or later limitation? I want to avoid defining dependency as future>=0.16 - by doing this I'd force users to install package that they don't need and won't use in a general case.

回答1:

kw = {}
try:
    import future
except ImportError:
    pass
else:
    kw['install_requires'] = ['future>=0.16']

setup(
    …
    **kw
)


回答2:

One workaround for this issue is to define this requirement only for the all target, so only if someone adds pylint[all]>=1.2.3 as a requirement they will have futures installed/upgraded.

At this moment I don't know another way to "ignore or upgrade" a dependency.

Also, I would avoid adding Python code to setup.py in order to make it "smart",... is a well known distribution anti-pattern ;)



回答3:

There is no supported way to tell pip or setuptools that a package needs to satisfy a constraint only if installed. There might be some hacks but I imagine they'll all be fragile and likely breaking in the future versions of pip/setuptools.

Honestly, the only good way is to document it for users that future < 16.0 would break pylint, in the appropriate location in the documentation.


Making your setup.py script contain conditional dependencies is something that has been strongly discouraged for some time now. Once a wheel is built, the package is installed with the same dependency information as the wheel holds - setup.py is not run on the end-user's system, only on the packager's system, which means any setup.py hack (like @phd's) would not be useful (since pylint distributes wheels).