Search code examples
python-3.xsetuptoolssdist

Setuptools: use build variants with different required packages


I want to make a source distribution (sdist), which needs to be different for the development and the target platform in terms of required packages.

More concretely, when I package for the Raspberry Pi (target platform), I don't require opencv-python, because OpenCV is built from sources there, but on development PCs (Ubuntu), I require opencv-python.

I tried to follow some tricks like this to pass in an --raspi parameter into the setup.py:

install_requires = [
    'opencv-python >= 4.1.1',
    ...
]

if "--raspi" in sys.argv:
    install_requires = [req for req in install_requires if not req.startswith('opencv-python')]
    sys.argv.remove("--raspi")

setup(
    ...,
    install_requires=install_requires
)

When I run python3 setup.py sdist --raspi, this approach works to a degree that the generated ./dist/mypackage.tar.gz/mypackage/mypackage.egg-info/requires.txt does not contain opencv-python anymore.

But when I run pip3 install ./dist/mypackage.tar.gz, I still get an error such as:

ERROR: Could not find a version that satisfies the requirement opencv-python>=4.1.1 (from mypackage==0.1) (from versions: none)

This is also when I pass --install-option="--raspi" to pip3 install, which I read somewhere would be a way to pass an argument into setup.py again when run from pip.

When I manually edit the distribution setup.py (./dist/mypackage.tar.gz/mypackage/setup.py) and remove opencv-python from the required packages, then the pip3 install works.

Are there other ways to have different sets or requirements for different builds? E.g. use two different setup.cfg files (how?), each specifying their set of packages? I wouldn't like that approach much, as I would have mostly duplication in those.


Solution

  • You can use the environment markers (as specified in PEP 508) to restrict the requirement to a particular platform:

    install_requires = [
        'opencv-python >= 4.1.1; platform_machine == "x86_64"'
    ]
    

    This will install opencv-python on an x86_64 arch, but skip it on ARM, PPC etc.