def fix_requires_python_marker(requires_python):
    from packaging.requirements import Requirement as PackagingRequirement

    marker_str = ""
    if any(
            requires_python.startswith(op)
            for op in Specifier._operators.keys()):
        spec_dict = defaultdict(set)
        # We are checking first if we have  leading specifier operator
        # if not, we can assume we should be doing a == comparison
        specifierset = list(SpecifierSet(requires_python))
        # for multiple specifiers, the correct way to represent that in
        # a specifierset is `Requirement('fakepkg; python_version<"3.0,>=2.6"')`
        marker_key = Variable("python_version")
        for spec in specifierset:
            operator, val = spec._spec
            cleaned_val = Value(val).serialize().replace('"', "")
            spec_dict[Op(operator).serialize()].add(cleaned_val)
        marker_str = " and ".join([
            "{0}{1}'{2}'".format(marker_key.serialize(), op, ",".join(vals))
            for op, vals in spec_dict.items()
        ])
    marker_to_add = PackagingRequirement(
        "fakepkg; {0}".format(marker_str)).marker
    return marker_to_add
Esempio n. 2
0
def test_specifier(op, val, expected):
    m = StringMarker(
        lhs=Variable('os_name'),
        op=Op(op),
        rhs=Value(val),
    )
    assert str(m) == expected
Esempio n. 3
0
def test_swap(op, val, expected):
    m = VersionMarker(
        lhs=Value(val),
        op=Op(op),
        rhs=Variable('python_version'),
    )
    assert str(m.specifier) == expected
Esempio n. 4
0
def test_merge(left_op, left_val, right_op, right_val, result):
    lm = StringMarker(
        lhs=Variable('os_name'),
        op=Op(left_op),
        rhs=Value(left_val),
    )
    rm = StringMarker(
        lhs=Variable('os_name'),
        op=Op(right_op),
        rhs=Value(right_val),
    )
    if result is None:
        with pytest.raises(TypeError):
            lm + rm
    else:
        merged = lm + rm
        assert str(merged) == result
Esempio n. 5
0
def test_merge(left_op, left_val, right_op, right_val, result):
    lm = VersionMarker(
        lhs=Variable('python_version'),
        op=Op(left_op),
        rhs=Value(left_val),
    )
    rm = VersionMarker(
        lhs=Variable('python_version'),
        op=Op(right_op),
        rhs=Value(right_val),
    )
    if result is None:
        with pytest.raises(TypeError):
            lm + rm
    else:
        merged = lm + rm
        assert str(merged.specifier) == result
Esempio n. 6
0
 def __add__(self, other: 'VersionMarker'):
     try:
         spec = self.specifier + other.specifier
     except TypeError:
         return NotImplemented
     return type(self)(
         lhs=self.lhs,
         op=Op(value=spec.operator),
         rhs=Value(value=str(spec.version)),
     )
Esempio n. 7
0
    def _convert_single_marker(lhs: Union[Value, Variable], op: Op,
                               rhs: Union[Value, Variable]) -> Union[Operation, BaseMarker]:
        var = lhs.value if type(lhs) is Variable else rhs.value
        if var in STRING_VARIABLES:
            return StringMarker(lhs=lhs, op=op, rhs=rhs)

        if var not in VERSION_VARIABLES:
            raise LookupError('unknown marker: {}'.format(var))

        if op.value == 'in' and type(rhs) is Value:
            values = rhs.value.split()
            markers = [VersionMarker(lhs=lhs, op=Op('=='), rhs=Value(value)) for value in values]
            return OrMarker(*markers)

        if op.value in {'in' 'not in'}:
            msg = 'unsupported operation for version marker {}: {}'
            raise ValueError(msg.format(var, op.value))

        return VersionMarker(lhs=lhs, op=op, rhs=rhs)
Esempio n. 8
0
def _marker_reduction(marker, extra):  # type: ignore
    """Convert internal packaging marker representation to interpretation which can be evaluated.

    As markers also depend on `extra' which will cause issues when evaluating marker in the solver
    environment, let's substitute `extra' marker with a condition which evaluates always to true.
    """
    if isinstance(marker, str):
        return marker

    if isinstance(marker, list):
        result_markers = []
        for nested_marker in marker:
            reduced_marker = _marker_reduction(nested_marker,
                                               extra)  # type: ignore
            result_markers.append(reduced_marker)

        return result_markers

    if marker[0].value != "extra":
        return marker

    extra.add(str(marker[2]))
    # A special case to handle extras in markers - substitute extra with a marker which always evaluates to true:
    return Variable("python_version"), Op(">="), Value("0.0")