Source code for ahbicht.expressions.base_transformer

"""
This module implements the base class for the condition check Transformers
that evaluate trees build from the condition_expression_parser.
"""

from abc import ABC, abstractmethod
from typing import Generic, Mapping, TypeVar

from lark import Token, Transformer, v_args

# All non-abstract transformers obey the following generic type constraints:
#   1. The methods of each transformer all have the same accepted argument type ("TSupportedArgumentNodeType").
#       This type is arbitrary but fixed per Transformer.
#   2. Also, all the methods of one transformer return objects of the same type ("TSupportedReturnType").
SupportedArgumentNode = TypeVar("SupportedArgumentNode")  # bound=ConditionNode)
# bound does not work because:
# error: Type argument "ahbicht.expressions.condition_nodes.EvaluatedFormatConstraint" of "BaseTransformer" must be a
# subtype of "ahbicht.expressions.condition_nodes.ConditionNode"  [type-var]
SupportedReturn = TypeVar("SupportedReturn")


[docs] @v_args(inline=True) # Children are provided as *args instead of a list argument class BaseTransformer(Transformer, ABC, Generic[SupportedArgumentNode, SupportedReturn]): # type: ignore[type-arg] """ Transformer that evaluates the trees built from the format constraint expressions. The input are the evaluated format constraint conditions in the form of ConditionNodes. After two nodes are evaluated in a composition, the resulting node has the node type EvalutatedComposition. The return value is a ConditionNode whose attribute `format_constraint_fulfilled` describes whether the format constraint expression is fulfilled or not. """ def __init__(self, input_values: Mapping[str, SupportedArgumentNode]) -> None: """ The input are the evaluated format constraint conditions in the form of ConditionNodes. :param input_values: something that maps a condition key (str) onto an argument """ super().__init__() self.input_values = input_values
[docs] def condition(self, token: Token) -> SupportedArgumentNode: """Returns ConditionNode of rule 'condition'""" try: condition_key = self.input_values[token.value] except KeyError as key_err: raise ValueError( "Please make sure that the input values contain all necessary condition_keys." ) from key_err return condition_key
[docs] def package(self, token: Token) -> SupportedArgumentNode: """Returns ConditionNode of rule package""" try: package_key = self.input_values[token.value] except KeyError as key_err: raise ValueError("Please make sure that the input values contain all necessary package_keys.") from key_err return package_key
[docs] @abstractmethod def and_composition(self, left: SupportedArgumentNode, right: SupportedArgumentNode) -> SupportedReturn: """Evaluates logical and_composition""" raise NotImplementedError("Has to be implemented by inheriting class.")
[docs] @abstractmethod def or_composition(self, left: SupportedArgumentNode, right: SupportedArgumentNode) -> SupportedReturn: """Evaluates logical (inclusive) or_composition""" raise NotImplementedError("Has to be implemented by inheriting class.")
[docs] @abstractmethod def xor_composition(self, left: SupportedArgumentNode, right: SupportedArgumentNode) -> SupportedReturn: """Evaluates exclusive xor_composition""" raise NotImplementedError("Has to be implemented by inheriting class.")