diff options
author | Steve Kowalik <steven@wedontsleep.org> | 2016-01-07 14:04:36 +1100 |
---|---|---|
committer | Steve Kowalik <steven@wedontsleep.org> | 2016-01-07 14:04:36 +1100 |
commit | 3bd5118eaa87b4f6598e0a473fec3623b6579d3b (patch) | |
tree | 22b9a1f65394dfee78f4327db2ee02cda2a14f55 | |
parent | 7d63ebffa598f12b55d9fd0a41768ec88ff70528 (diff) | |
download | external_python_setuptools-3bd5118eaa87b4f6598e0a473fec3623b6579d3b.tar.gz external_python_setuptools-3bd5118eaa87b4f6598e0a473fec3623b6579d3b.tar.bz2 external_python_setuptools-3bd5118eaa87b4f6598e0a473fec3623b6579d3b.zip |
Destroy MarkerEvaluation for being pointless, fix two silly mistakes in tests and update packaging changes.
-rw-r--r-- | Makefile | 2 | ||||
-rw-r--r-- | pkg_resources/__init__.py | 181 | ||||
-rw-r--r-- | pkg_resources/_vendor/packaging/markers.py | 4 | ||||
-rw-r--r-- | pkg_resources/_vendor/packaging/requirements.py | 13 | ||||
-rw-r--r-- | pkg_resources/_vendor/packaging/specifiers.py | 6 | ||||
-rw-r--r-- | pkg_resources/_vendor/vendored.txt | 1 | ||||
-rw-r--r-- | pkg_resources/api_tests.txt | 2 | ||||
-rw-r--r-- | pkg_resources/tests/test_markers.py | 12 |
8 files changed, 46 insertions, 175 deletions
@@ -7,4 +7,6 @@ update-vendored: pip install -r pkg_resources/_vendor/vendored.txt -t pkg_resources/_vendor/ sed -i -e 's/ \(pyparsing\)/ pkg_resources._vendor.\1/' \ pkg_resources/_vendor/packaging/*.py + sed -i -e 's/ \(six\)/ pkg_resources._vendor.\1/' \ + pkg_resources/_vendor/packaging/*.py rm -rf pkg_resources/_vendor/*.{egg,dist}-info diff --git a/pkg_resources/__init__.py b/pkg_resources/__init__.py index d81430c7..aa221347 100644 --- a/pkg_resources/__init__.py +++ b/pkg_resources/__init__.py @@ -1407,170 +1407,31 @@ def to_filename(name): return name.replace('-','_') -class MarkerEvaluation(object): - values = { - 'os_name': lambda: os.name, - 'sys_platform': lambda: sys.platform, - 'python_full_version': platform.python_version, - 'python_version': lambda: platform.python_version()[:3], - 'platform_version': platform.version, - 'platform_machine': platform.machine, - 'platform_python_implementation': platform.python_implementation, - 'python_implementation': platform.python_implementation, - } - - @classmethod - def is_invalid_marker(cls, text): - """ - Validate text as a PEP 508 environment marker; return an exception - if invalid or False otherwise. - """ - try: - cls.evaluate_marker(text) - except packaging.markers.InvalidMarker as e: - e.filename = None - e.lineno = None - return e - return False - - @staticmethod - def normalize_exception(exc): - """ - Given a SyntaxError from a marker evaluation, normalize the error - message: - - Remove indications of filename and line number. - - Replace platform-specific error messages with standard error - messages. - """ - subs = { - 'unexpected EOF while parsing': 'invalid syntax', - 'parenthesis is never closed': 'invalid syntax', - } - exc.filename = None - exc.lineno = None - exc.msg = subs.get(exc.msg, exc.msg) - return exc - - @classmethod - def and_test(cls, nodelist): - # MUST NOT short-circuit evaluation, or invalid syntax can be skipped! - items = [ - cls.interpret(nodelist[i]) - for i in range(1, len(nodelist), 2) - ] - return functools.reduce(operator.and_, items) - - @classmethod - def test(cls, nodelist): - # MUST NOT short-circuit evaluation, or invalid syntax can be skipped! - items = [ - cls.interpret(nodelist[i]) - for i in range(1, len(nodelist), 2) - ] - return functools.reduce(operator.or_, items) - - @classmethod - def atom(cls, nodelist): - t = nodelist[1][0] - if t == token.LPAR: - if nodelist[2][0] == token.RPAR: - raise SyntaxError("Empty parentheses") - return cls.interpret(nodelist[2]) - msg = "Language feature not supported in environment markers" - raise SyntaxError(msg) - - @classmethod - def comparison(cls, nodelist): - if len(nodelist) > 4: - msg = "Chained comparison not allowed in environment markers" - raise SyntaxError(msg) - comp = nodelist[2][1] - cop = comp[1] - if comp[0] == token.NAME: - if len(nodelist[2]) == 3: - if cop == 'not': - cop = 'not in' - else: - cop = 'is not' - try: - cop = cls.get_op(cop) - except KeyError: - msg = repr(cop) + " operator not allowed in environment markers" - raise SyntaxError(msg) - return cop(cls.evaluate(nodelist[1]), cls.evaluate(nodelist[3])) - - @classmethod - def get_op(cls, op): - ops = { - symbol.test: cls.test, - symbol.and_test: cls.and_test, - symbol.atom: cls.atom, - symbol.comparison: cls.comparison, - 'not in': lambda x, y: x not in y, - 'in': lambda x, y: x in y, - '==': operator.eq, - '!=': operator.ne, - '<': operator.lt, - '>': operator.gt, - '<=': operator.le, - '>=': operator.ge, - } - if hasattr(symbol, 'or_test'): - ops[symbol.or_test] = cls.test - return ops[op] - - @classmethod - def evaluate_marker(cls, text, extra=None): - """ - Evaluate a PEP 508 environment marker on CPython 2.4+. - Return a boolean indicating the marker result in this environment. - Raise InvalidMarker if marker is invalid. - - This implementation uses the 'pyparsing' module. - """ - marker = packaging.markers.Marker(text) - return marker.evaluate() +def invalid_marker(text): + """ + Validate text as a PEP 508 environment marker; return an exception + if invalid or False otherwise. + """ + try: + evaluate_marker(text) + except packaging.markers.InvalidMarker as e: + e.filename = None + e.lineno = None + return e + return False - @classmethod - def interpret(cls, nodelist): - while len(nodelist)==2: nodelist = nodelist[1] - try: - op = cls.get_op(nodelist[0]) - except KeyError: - raise SyntaxError("Comparison or logical expression expected") - return op(nodelist) - @classmethod - def evaluate(cls, nodelist): - while len(nodelist)==2: nodelist = nodelist[1] - kind = nodelist[0] - name = nodelist[1] - if kind==token.NAME: - try: - op = cls.values[name] - except KeyError: - raise SyntaxError("Unknown name %r" % name) - return op() - if kind==token.STRING: - s = nodelist[1] - if not cls._safe_string(s): - raise SyntaxError( - "Only plain strings allowed in environment markers") - return s[1:-1] - msg = "Language feature not supported in environment markers" - raise SyntaxError(msg) +def evaluate_marker(text, extra=None): + """ + Evaluate a PEP 508 environment marker. + Return a boolean indicating the marker result in this environment. + Raise InvalidMarker if marker is invalid. - @staticmethod - def _safe_string(cand): - return ( - cand[:1] in "'\"" and - not cand.startswith('"""') and - not cand.startswith("'''") and - '\\' not in cand - ) + This implementation uses the 'pyparsing' module. + """ + marker = packaging.markers.Marker(text) + return marker.evaluate() -invalid_marker = MarkerEvaluation.is_invalid_marker -evaluate_marker = MarkerEvaluation.evaluate_marker class NullProvider: """Try to implement resources and metadata for arbitrary PEP 302 loaders""" diff --git a/pkg_resources/_vendor/packaging/markers.py b/pkg_resources/_vendor/packaging/markers.py index e9c6805a..db8f1c25 100644 --- a/pkg_resources/_vendor/packaging/markers.py +++ b/pkg_resources/_vendor/packaging/markers.py @@ -55,7 +55,7 @@ class Value(Node): VARIABLE = ( L("implementation_version") | - L("python_implementation") | + L("platform_python_implementation") | L("implementation_name") | L("python_full_version") | L("platform_release") | @@ -209,7 +209,7 @@ def default_environment(): "platform_system": platform.system(), "platform_version": platform.version(), "python_full_version": platform.python_version(), - "python_implementation": platform.python_implementation(), + "platform_python_implementation": platform.python_implementation(), "python_version": platform.python_version()[:3], "sys_platform": sys.platform, } diff --git a/pkg_resources/_vendor/packaging/requirements.py b/pkg_resources/_vendor/packaging/requirements.py index dc3672e7..658716c6 100644 --- a/pkg_resources/_vendor/packaging/requirements.py +++ b/pkg_resources/_vendor/packaging/requirements.py @@ -9,7 +9,7 @@ import re from pkg_resources._vendor.pyparsing import stringStart, stringEnd, originalTextFor, ParseException from pkg_resources._vendor.pyparsing import ZeroOrMore, Word, Optional, Regex, Combine from pkg_resources._vendor.pyparsing import Literal as L # noqa -from six.moves.urllib import parse as urlparse +from pkg_resources._vendor.six.moves.urllib import parse as urlparse from .markers import MARKER_EXPR, Marker from .specifiers import LegacySpecifier, Specifier, SpecifierSet @@ -73,6 +73,12 @@ REQUIREMENT = stringStart + NAMED_REQUIREMENT + stringEnd class Requirement(object): + """Parse a requirement. + + Parse a given requirement string into its parts, such as name, specifier, + URL, and extras. Raises InvalidRequirement on a badly-formed requirement + string. + """ # TODO: Can we test whether something is contained within a requirement? # If so how do we do that? Do we need to test against the _name_ of @@ -82,9 +88,10 @@ class Requirement(object): def __init__(self, requirement_string): try: req = REQUIREMENT.parseString(requirement_string) - except ParseException: + except ParseException as e: raise InvalidRequirement( - "Invalid requirement: {0!r}".format(requirement_string)) + "Invalid requirement, parse error at \"{0!r}\"".format( + requirement_string[e.loc:e.loc + 8])) self.name = req.name if req.url: diff --git a/pkg_resources/_vendor/packaging/specifiers.py b/pkg_resources/_vendor/packaging/specifiers.py index b1fca708..cef90084 100644 --- a/pkg_resources/_vendor/packaging/specifiers.py +++ b/pkg_resources/_vendor/packaging/specifiers.py @@ -225,7 +225,8 @@ class LegacySpecifier(_IndividualSpecifier): """ ) - _regex = re.compile(r"^\s*" + _regex_str + r"\s*$", re.X | re.I) + _regex = re.compile( + r"^\s*" + _regex_str + r"\s*$", re.VERBOSE | re.IGNORECASE) _operators = { "==": "equal", @@ -366,7 +367,8 @@ class Specifier(_IndividualSpecifier): """ ) - _regex = re.compile(r"^\s*" + _regex_str + r"\s*$", re.X | re.I) + _regex = re.compile( + r"^\s*" + _regex_str + r"\s*$", re.VERBOSE | re.IGNORECASE) _operators = { "~=": "compatible", diff --git a/pkg_resources/_vendor/vendored.txt b/pkg_resources/_vendor/vendored.txt index 27bbc925..fcb72075 100644 --- a/pkg_resources/_vendor/vendored.txt +++ b/pkg_resources/_vendor/vendored.txt @@ -1,2 +1,3 @@ packaging==15.3 pyparsing==2.0.6 +six==1.10.0 diff --git a/pkg_resources/api_tests.txt b/pkg_resources/api_tests.txt index 2458c322..9df56b4b 100644 --- a/pkg_resources/api_tests.txt +++ b/pkg_resources/api_tests.txt @@ -382,7 +382,7 @@ Environment Markers >>> print(im("os.open=='y'")) Invalid marker: "os.open=='y'" - >>> em("'linux' in sys_platform") + >>> em("sys_platform=='win32'") == (sys.platform=='win32') True >>> em("python_version >= '2.6'") diff --git a/pkg_resources/tests/test_markers.py b/pkg_resources/tests/test_markers.py index 2f4b52c5..0af3089e 100644 --- a/pkg_resources/tests/test_markers.py +++ b/pkg_resources/tests/test_markers.py @@ -1,12 +1,10 @@ try: - import unittest.mock as mock + import unitest.mock as mock except ImportError: - import mock + import mock from pkg_resources import evaluate_marker - -@mock.patch.dict('pkg_resources.MarkerEvaluation.values', - python_full_version=mock.Mock(return_value='2.7.10')) -def test_ordering(): - assert evaluate_marker("python_full_version > '2.7.3'") is True +@mock.patch('platform.python_version', return_value='2.7.10') +def test_ordering(python_version_mock): + assert evaluate_marker("python_full_version > '2.7.3'") is True |