diff --git a/checkbox-ng/plainbox/impl/new_resource.py b/checkbox-ng/plainbox/impl/new_resource.py index f0c851a82..908ada05a 100644 --- a/checkbox-ng/plainbox/impl/new_resource.py +++ b/checkbox-ng/plainbox/impl/new_resource.py @@ -171,8 +171,13 @@ def __call__(self, *args): def from_unary_op(cls, parsed_ast): if not isinstance(parsed_ast.op, ast.USub): raise ValueError("Unsupported operator {}".format(parsed_ast)) - parsed_ast.operand.value *= -1 - return cls(parsed_ast.operand) + operand = getter_from_ast(parsed_ast.operand) + if not isinstance(operand, ConstantGetter): + raise ValueError( + "`-` operator can't be applied to non-constant operands" + ) + operand.value *= -1 + return cls(operand) def __str__(self): return str(self.value) @@ -219,11 +224,25 @@ def __str__(self): legacy_getters = {} if sys.version_info[0] == 3 and sys.version_info[1] < 8: - # older version of python have + from collections import namedtuple + + # older version of python have slightly different nodes to parse + # constants. Here we wrap them for forward compatibility putting the old + # attribute where the ConstantGetter expects to find it + Wrapper = namedtuple("Wrapper", ["value"]) + + def wrapping(attr): + def _f(parsed_ast): + wrapped_parsed_ast = Wrapper(getattr(parsed_ast, attr)) + return ConstantGetter(wrapped_parsed_ast) + + return _f + legacy_getters = { - ast.Str: ConstantGetter, - ast.Num: ConstantGetter, - ast.Bytes: ConstantGetter, + ast.Str: wrapping("s"), + ast.Num: wrapping("n"), + ast.Bytes: wrapping("s"), + # this actually uses .value ast.NameConstant: ConstantGetter, }