From 8cdb41cf1264e71fd2f479efa7decd38c1f91cfa Mon Sep 17 00:00:00 2001 From: Claudiu Popa Date: Mon, 24 Nov 2014 11:04:43 +0200 Subject: Support platform-specific requirements files This patch adds support for choosing a requirements file, based on the current OS, with the format 'requirements-{osname}'. This can be combined with the current approach of choosing a requirement file based on the Python version. The motivation for this is to replace conditional choosing of packages inside setup.py. Change-Id: I30c56082bb9b9bcd80128eedcef17b6beb793cf8 --- doc/source/index.rst | 14 ++++++++++++-- pbr/packaging.py | 25 ++++++++++++++++++++++--- pbr/tests/test_packaging.py | 27 +++++++++++++++++++++++++++ 3 files changed, 61 insertions(+), 5 deletions(-) diff --git a/doc/source/index.rst b/doc/source/index.rst index 918be40..f36fc6f 100644 --- a/doc/source/index.rst +++ b/doc/source/index.rst @@ -107,11 +107,21 @@ You can also have a requirement file for each specific major version of Python. If you want to have a different package list for Python 3, just drop a requirements-py3.txt, and it will be used instead. +It's also possible to select a requirement file specific for an OS. The format +is requirements-{osname}.txt, where ``{osname}`` is the equivalent of +``platform.system()``. The two approaches, Python version and OS version, can +be combined. + The requirement files are tried in that order (N being the Python major -version number used to install the package): +version number used to install the package and OS being the current +platform's name in lowercase, retrieved with ``platform.system()``): +* requirements-OS-pyN.txt +* tools/pip-requires-OS-pyN +* requirements-OS.txt +* tools/pip-requires-OS * requirements-pyN.txt -* tools/pip-requires-py3 +* tools/pip-requires-pyN * requirements.txt * tools/pip-requires diff --git a/pbr/packaging.py b/pbr/packaging.py index 99fa2ef..18d18e6 100644 --- a/pbr/packaging.py +++ b/pbr/packaging.py @@ -24,8 +24,11 @@ from distutils.command import install as du_install import distutils.errors from distutils import log import email +import functools import io +import itertools import os +import platform import re import subprocess import sys @@ -56,10 +59,26 @@ def get_requirements_files(): # Returns a list composed of: # - REQUIREMENTS_FILES with -py2 or -py3 in the name # (e.g. requirements-py3.txt) + # - REQUIREMENTS_FILES with -{platform.system} in the name + # (e.g. requirements-windows.txt) + # - REQUIREMENTS_FILES with both Python version and platform's + # system in the name + # (e.g. requirements-freebsd-py2.txt) # - REQUIREMENTS_FILES - return (list(map(('-py' + str(sys.version_info[0])).join, - map(os.path.splitext, REQUIREMENTS_FILES))) - + list(REQUIREMENTS_FILES)) + pyversion = sys.version_info[0] + system = platform.system().lower() + parts = list(map(os.path.splitext, REQUIREMENTS_FILES)) + + version_cb = functools.partial("{1}-py{0}{2}".format, pyversion) + platform_cb = functools.partial("{1}-{0}{2}".format, system) + both_cb = functools.partial("{2}-{0}-py{1}{3}".format, system, pyversion) + + return list(itertools.chain( + itertools.starmap(both_cb, parts), + itertools.starmap(platform_cb, parts), + itertools.starmap(version_cb, parts), + REQUIREMENTS_FILES, + )) def append_text_list(config, key, text_list): diff --git a/pbr/tests/test_packaging.py b/pbr/tests/test_packaging.py index a067945..0fdc5bb 100644 --- a/pbr/tests/test_packaging.py +++ b/pbr/tests/test_packaging.py @@ -39,6 +39,7 @@ # BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS import os +import sys import tempfile import fixtures @@ -214,6 +215,32 @@ class TestNestedRequirements(base.BaseTestCase): self.assertEqual(result, ['pbr']) +class TestGetRequirements(base.BaseTestCase): + + def test_get_requirements_file(self): + platforms = ['Windows', 'Freebsd', 'Darwin', 'Linux'] + version = sys.version_info[0] + + with mock.patch('platform.system') as platform_system: + platform_system.side_effect = platforms + + for platform in map(str.lower, platforms): + expected = [ + 'requirements-{plat}-py{ver}.txt'.format( + plat=platform, ver=version), + 'tools/pip-requires-{plat}-py{ver}'.format( + plat=platform, ver=version), + 'requirements-{0}.txt'.format(platform), + 'tools/pip-requires-{0}'.format(platform), + 'requirements-py{0}.txt'.format(version), + 'tools/pip-requires-py{0}'.format(version), + 'requirements.txt', + 'tools/pip-requires', + ] + files = packaging.get_requirements_files() + self.assertEqual(expected, files) + + class TestVersions(base.BaseTestCase): scenarios = [ -- cgit v1.2.1