ahbicht.expressions package

Submodules

ahbicht.expressions.ahb_expression_evaluation module

This module evaluates the parsed ahb expression tree. The AhbExpressionTransformer defines the rules how the different parts of the parsed tree are handled.

The used terms are defined in the README.md.

class ahbicht.expressions.ahb_expression_evaluation.AhbExpressionTransformer[source]

Bases: Transformer

Transformer, that evaluates the trees built from the ahb expressions. The input are the conditions as defined in the AHBs in the form of ConditionNodes. It returns a list of the seperated requirement indicators with their respective condition expressions already evaluated to booleans.

CONDITION_EXPRESSION(condition_expression: Token) str[source]

Returns the condition expression.

MODAL_MARK(modal_mark: Token) ModalMark[source]

Returns the modal mark.

PREFIX_OPERATOR(prefix_operator: Token) PrefixOperator[source]

Returns the prefix operator.

ahb_expression(list_of_single_requirement_indicator_expressions: List[AhbExpressionEvaluationResult | Awaitable[AhbExpressionEvaluationResult]]) Awaitable[AhbExpressionEvaluationResult][source]

Returns the requirement indicator with its condition expressions already evaluated to booleans. If there are more than one modal mark the first whose conditions are fulfilled is returned or the last of the list if they are all unfulfilled.

requirement_indicator(requirement_indicator: PrefixOperator | ModalMark) AhbExpressionEvaluationResult[source]

If there is no condition expression but only a requirement indicator, all evaluations are automatically set to True.

single_requirement_indicator_expression(requirement_indicator: PrefixOperator | ModalMark, condition_expression) Awaitable[AhbExpressionEvaluationResult][source]

Evaluates the condition expression of the respective requirement indicator expression and returns a list of the seperated requirement indicators with their results of the condition check.

async ahbicht.expressions.ahb_expression_evaluation.evaluate_ahb_expression_tree(parsed_tree: Tree) AhbExpressionEvaluationResult[source]

Evaluates the tree built from the ahb expressions with the help of the AhbExpressionTransformer.

Parameters:

parsed_tree – Tree

Returns:

the result of the overall condition check (including requirement constraints, format constraints, several modal marks)

ahbicht.expressions.ahb_expression_parser module

This module parses a given ahb expression like “Muss [59]U([123]O[456]) Soll [53]” or “X [59]U[53]” using the parsing library lark: https://lark-parser.readthedocs.io/en/latest/ The goal is to separate the requirement indicator (i.e. Muss, Soll, Kann, X, O, U) from the condition expression and also several modal marks expressions if there are more than one.

ahbicht.expressions.base_transformer module

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

class ahbicht.expressions.base_transformer.BaseTransformer(input_values: Mapping[str, SupportedArgumentNode])[source]

Bases: Transformer, ABC, Generic[SupportedArgumentNode, SupportedReturn]

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 fulfiled or not.

abstract and_composition(left: SupportedArgumentNode, right: SupportedArgumentNode) SupportedReturn[source]

Evaluates logical and_composition

condition(token: Token) SupportedArgumentNode[source]

Returns ConditionNode of rule ‘condition’

abstract or_composition(left: SupportedArgumentNode, right: SupportedArgumentNode) SupportedReturn[source]

Evaluates logical (inclusive) or_composition

package(token: Token) SupportedArgumentNode[source]

Returns ConditionNode of rule package

abstract xor_composition(left: SupportedArgumentNode, right: SupportedArgumentNode) SupportedReturn[source]

Evaluates exclusive xor_composition

ahbicht.expressions.condition_expression_parser module

This module parses a condition expression like “[59] U ([123] O [456])” into a tree structur using the parsing library lark: https://lark-parser.readthedocs.io/en/latest/

The used terms are defined in the README_conditions.md.

async ahbicht.expressions.condition_expression_parser.extract_categorized_keys(condition_expression: str, resolve_packages: bool = False, replace_time_conditions: bool = False) CategorizedKeyExtract[source]

Parses the given condition expression and returns CategorizedKeyExtract as a template for content evaluation.

ahbicht.expressions.condition_expression_parser.extract_categorized_keys_from_tree(tree_or_list: Tree | List[str], sanitize: bool = False) CategorizedKeyExtract[source]

find different types of condition nodes inside the given tree or list of keys. The types are differentiated by their number range. See ‘Allgemeine Festlegungen’ from EDI@Energy.

ahbicht.expressions.condition_nodes module

This module contains the abstract class ConditionNode, which specifies the nodes of the parsed tree. The type of the subclass is the decisive factor on how the respective node is handled in the context of the compositions it is used in. There are three possible input nodes (RequirementConstraint, Hint and FormatConstraint) and the EvaluatedComposition node which results from a combination of two nodes (of all possible types).

The used terms are defined in the README_conditions.md.

class ahbicht.expressions.condition_nodes.ConditionFulfilledValue(value)[source]

Bases: str, Enum

Possible values to describe the state of a condition in the condition_fulfilled attribute of the ConditionNodes.

FULFILLED = 'FULFILLED'

if condition is fulfilled

NEUTRAL = 'NEUTRAL'

a hint or unevaluated format constraint which does not have a status of being fulfilled or not

UNFULFILLED = 'UNFULFILLED'

if condition is not fulfilled

UNKNOWN = 'UNKNOWN'

if it cannot be checked if condition is fulfilled (e.g. “Wenn vorhanden”)

class ahbicht.expressions.condition_nodes.ConditionKeyNodeMixin(*, condition_key: str)[source]

Bases: ABC

Nodes that have a condition key.

condition_key: str
class ahbicht.expressions.condition_nodes.ConditionNode(*, conditions_fulfilled: ConditionFulfilledValue)[source]

Bases: ABC

This abstract class specifies the nodes of the parsed tree. The type of the subclass is the decisive factor on how the respective node is handled in the context of the compositions it is used in.

conditions_fulfilled: ConditionFulfilledValue
class ahbicht.expressions.condition_nodes.EvaluatedComposition(*, conditions_fulfilled: ConditionFulfilledValue, hint: str | None = None, format_constraints_expression: str | None = None)[source]

Bases: ConditionNode

Node which is returned after a composition of two nodes is evaluated.

format_constraints_expression: str | None

an expression that consists of (initially unevaluated) format constraints that the evaluated field needs to obey

hint: str | None
class ahbicht.expressions.condition_nodes.EvaluatedFormatConstraint(format_constraint_fulfilled: bool, error_message: str | None = None)[source]

Bases: object

This class is the base class of all evaluated format constraints. They are used in the context of the Mussfeldprüfung after the format constraints are evaluated to see if the format constraint expression is fulfilled or not.

error_message: str | None
format_constraint_fulfilled: bool
class ahbicht.expressions.condition_nodes.EvaluatedFormatConstraintSchema(*, only: Sequence[str] | AbstractSet[str] | None = None, exclude: Sequence[str] | AbstractSet[str] = (), many: bool = False, context: dict | None = None, load_only: Sequence[str] | AbstractSet[str] = (), dump_only: Sequence[str] | AbstractSet[str] = (), partial: bool | Sequence[str] | AbstractSet[str] | None = None, unknown: str | None = None)[source]

Bases: Schema

A schema to (de)serialize EvaluatedFormatConstraints.

deserialize(data, **kwargs) EvaluatedFormatConstraint[source]

converts the barely typed data dictionary into an actual EvaluatedFormatConstraint :param data: :param kwargs: :return:

opts: SchemaOpts = <marshmallow.schema.SchemaOpts object>
class ahbicht.expressions.condition_nodes.FormatConstraint(*, condition_key: str, conditions_fulfilled: ConditionFulfilledValue)[source]

Bases: ConditionNode, ConditionKeyNodeMixin

This class is the base class of all format constraints. FormatConstraints describe that data have to obey certain rules, meaning those conditions with an outcome that does not change whether data are obligatory or not but validates existing data.

class ahbicht.expressions.condition_nodes.Hint(*, condition_key: str, conditions_fulfilled: ConditionFulfilledValue = ConditionFulfilledValue.NEUTRAL, hint: str)[source]

Bases: ConditionNode, ConditionKeyNodeMixin

A so called ‘Hinweis’, just a hint, even if it is worded like a condition, e.g. “Hinweis: ‘Es ist der alte MSB zu verwenden’”

conditions_fulfilled: ConditionFulfilledValue
hint: str
class ahbicht.expressions.condition_nodes.RequirementConstraint(*, condition_key: str, conditions_fulfilled: ConditionFulfilledValue)[source]

Bases: ConditionNode, ConditionKeyNodeMixin

Bedingung, with a requirement constraint, e.g. “falls SG2+IDE+CCI == EHZ”

class ahbicht.expressions.condition_nodes.UnevaluatedFormatConstraint(*, condition_key: str, conditions_fulfilled: ConditionFulfilledValue = ConditionFulfilledValue.NEUTRAL)[source]

Bases: FormatConstraint

This class is the base class of all unevaluated format constraints. They are used in the context of the Mussfeldprüfung where the constraints are collected but not evaluated yet.

conditions_fulfilled: ConditionFulfilledValue

ahbicht.expressions.enums module

Enums used in AHB and condition expressions.

class ahbicht.expressions.enums.LogicalOperator(value)[source]

Bases: StrEnum

Logical operators connect two tokens.

LAND = 'U'

logical AND, also denoted as “∧”, used in and_composition

LOR = 'O'

logical OR, also denoted as “∨”, used in or_composition

XOR = 'X'

logical excluxive OR (XOR), also denoted as “⊻”, used in xor_composition

class ahbicht.expressions.enums.ModalMark(value)[source]

Bases: StrEnum

A modal mark describes if information are obligatory or not. The German term is “Merkmal”. The modal marks are defined by the EDI Energy group (see edi-energy.de → Dokumente → Allgemeine Festlegungen). The modal mark stands alone or before a condition expression. It can be the start of several requirement indicator expressions in one AHB expression.

KANN = 'KANN'

German term for “Can”. Optional

MUSS = 'MUSS'

German term for “Must”. Is required for the correct structure of the message. If the following condition is not fulfilled, the information must not be given (“must not”)

SOLL = 'SOLL'

German term for “Should”. Is required for technical reasons. Always followed by a condition. If the following condition is not fulfilled, the information must not be given.

class ahbicht.expressions.enums.PrefixOperator(value)[source]

Bases: StrEnum

Operator which does not function to combine conditions, but as requirement indicator. It stands alone or in front of a condition expression. Please find detailed descriptions of the operators and their usage in the “Allgemeine Festlegungen”. Note that with MaKo2022 introced 2022-04-01 the “O” and “U” prefix operators will be deprecated. Refer to the “Allgemeine Festlegungen” valid up to 2022-04-01 for deprecated “O” and “U”.

O = 'O'

The “O” operator means that at least one out of multiple possible qualifiers/codes has to be given. This is typically found when describing ways to contact a market partner (CTA): You can use email or phone or fax but you have to provide at least one of the given possibilities. The usage of “O” as a prefix operator is deprecated since 2022-04-01. Note that “O” can also be used as a “logical or” (aka “lor”) operator in condition expressions. The prefix operator works differently from the logical operator in condition expressions! The usage of “O” as logical operator is also deprecated since 2022-04-01. It will be replaced with the “∨” symbol.

U = 'U'

The “U” operator means that all provided qualifiers/codes have to be used. The usage of “U” as a prefix operator is deprecated since 2022-04-01. Note that “U” can also be used as a “logical and” (aka “land”) operator in condition expressions. The prefix operator works differently from the logical operator in condition expressions! The usage of “U” as logical operator is also deprecated since 2022-04-01. It will be replaced with the “∧” symbol.

X = 'X'

The “X” operator. See “Allgemeine Festlegungen” Kapitel 6.8.1. Usually this just means something is required or required under circumstances defined in a trailing condition expression. It shall be read as “exclusive or” regarding how qualifiers/codes shall be used from a finite set. Note that “X” can also be used as “logical exclusive or” (aka “xor”) operator in condition expressions. The prefix operator works differently from the logical operator in condition expressions! The usage of “X” as logical operator is deprecated since 2022-04-01. It will be replaced with the “⊻” symbol.

ahbicht.expressions.enums.RequirementIndicator

A Requirement Indicator is either the Merkmal ModalMark or the PrefixOperator of the data element/data element group/segment/segment group at which it is used.

alias of Union[PrefixOperator, ModalMark]

class ahbicht.expressions.enums.RequirementIndicatorSchema(*, only: Sequence[str] | AbstractSet[str] | None = None, exclude: Sequence[str] | AbstractSet[str] = (), many: bool = False, context: dict | None = None, load_only: Sequence[str] | AbstractSet[str] = (), dump_only: Sequence[str] | AbstractSet[str] = (), partial: bool | Sequence[str] | AbstractSet[str] | None = None, unknown: str | None = None)[source]

Bases: Schema

a helper schema because marshmallow does not support something like fields.Union out of the box

opts: SchemaOpts = <marshmallow.schema.SchemaOpts object>
post_dump(data, **kwargs)[source]

returns the enum value as upper case

post_load(data, **kwargs) PrefixOperator | ModalMark[source]

tries to parse the data as either PrefixOperator or ModalMark

pre_load(data, **kwargs) Dict[Literal['value'], str][source]

puts the value in an artificial dictionary

ahbicht.expressions.expression_builder module

Module to create expressions from scratch.

class ahbicht.expressions.expression_builder.ExpressionBuilder[source]

Bases: Generic[SupportedNodes], ABC

Class that helps to create expression strings. It separates the logical operation (connect two conditions with a logical operator) from the implementation which might differ depending on the condition type and other circumstances.

abstract get_expression() str | None[source]

Returns the expression string or none if there is no expression. :return:

abstract land(other: SupportedNodes)[source]

connects the expression with a logical and (LAND) :param other: condition or expression to be connected to the expression :return:

abstract lor(other: SupportedNodes)[source]

connects the expression with a logical or (LOR) :param other: condition or expression to be connected to the expression :return:

abstract xor(other: SupportedNodes)[source]

connects the expression with an exclusive or (XOR) :param other: condition or expression to be connected to the expression :return:

class ahbicht.expressions.expression_builder.FormatConstraintExpressionBuilder(init_condition_or_expression: EvaluatedComposition | UnevaluatedFormatConstraint | str | None | RequirementConstraint | Hint | Type[ConditionNode])[source]

Bases: ExpressionBuilder[Union[EvaluatedComposition, UnevaluatedFormatConstraint, str, None, RequirementConstraint, Hint, Type[ConditionNode]]]

Class to create expressions that consist of FormatConstraints

get_expression() str | None[source]

Returns the expression string or none if there is no expression. :return:

land(other: EvaluatedComposition | UnevaluatedFormatConstraint | str | None | RequirementConstraint | Hint | Type[ConditionNode]) ExpressionBuilder[source]

connects the expression with a logical and (LAND) :param other: condition or expression to be connected to the expression :return:

lor(other: EvaluatedComposition | UnevaluatedFormatConstraint | str | None | RequirementConstraint | Hint | Type[ConditionNode]) ExpressionBuilder[source]

connects the expression with a logical or (LOR) :param other: condition or expression to be connected to the expression :return:

xor(other: EvaluatedComposition | UnevaluatedFormatConstraint | str | None | RequirementConstraint | Hint | Type[ConditionNode]) ExpressionBuilder[source]

connects the expression with an exclusive or (XOR) :param other: condition or expression to be connected to the expression :return:

class ahbicht.expressions.expression_builder.FormatErrorMessageExpressionBuilder(init_condition: EvaluatedFormatConstraint)[source]

Bases: ExpressionBuilder[EvaluatedFormatConstraint]

Class to build the error messages for the format constraint evaluation.

get_expression() str | None[source]

Returns the expression string or none if there is no expression. :return:

land(other: EvaluatedFormatConstraint) ExpressionBuilder[source]

connects the expression with a logical and (LAND) :param other: condition or expression to be connected to the expression :return:

lor(other: EvaluatedFormatConstraint) ExpressionBuilder[source]

connects the expression with a logical or (LOR) :param other: condition or expression to be connected to the expression :return:

xor(other: EvaluatedFormatConstraint) ExpressionBuilder[source]

connects the expression with an exclusive or (XOR) :param other: condition or expression to be connected to the expression :return:

class ahbicht.expressions.expression_builder.HintExpressionBuilder(init_condition: _ClassesWithHintAttribute | None)[source]

Bases: ExpressionBuilder[ClassesWithHintAttribute]

Allows connecting hints with logical operations.

get_expression() str | None[source]

Returns the expression string or none if there is no expression. :return:

static get_hint_text(hinty_object: _ClassesWithHintAttribute | None) str | None[source]

get the hint from a Hint instance or plain string :param hinty_object: :return: hint if there is any, None otherwise

land(other: _ClassesWithHintAttribute | None) ExpressionBuilder[source]

connects the expression with a logical and (LAND) :param other: condition or expression to be connected to the expression :return:

lor(other: _ClassesWithHintAttribute | None) ExpressionBuilder[source]

connects the expression with a logical or (LOR) :param other: condition or expression to be connected to the expression :return:

xor(other: _ClassesWithHintAttribute | None) ExpressionBuilder[source]

connects the expression with an exclusive or (XOR) :param other: condition or expression to be connected to the expression :return:

ahbicht.expressions.expression_resolver module

This module makes it possible to parse expressions including all their subexpressions, if present. for example ahb_expressions which contain condition_expressions or condition_expressions which contain packages. Parsing expressions that are nested into other expressions is referred to as “resolving”.

class ahbicht.expressions.expression_resolver.AhbExpressionResolverTransformer(visit_tokens: bool = True)[source]

Bases: Transformer

Resolves the condition_expressions inside an ahb_expression.

CONDITION_EXPRESSION(expression)[source]

Replacing the expression_condition with its parsed tree.

class ahbicht.expressions.expression_resolver.PackageExpansionTransformer[source]

Bases: Transformer

The PackageExpansionTransformer expands packages inside a tree to condition expressions by using a PackageResolver.

package(tokens: List[Token]) Awaitable[Tree][source]

try to resolve the package using the injected PackageResolver

class ahbicht.expressions.expression_resolver.TimeConditionTransformer(visit_tokens: bool = True)[source]

Bases: Transformer

The TimeConditionEvaluator replaces “time conditions” (aka “UB1”, “UB2”, “UB3”) with evaluatable format constraints. This is not what BDEW suggests us to do in the “Allgemeine Festlegungen”. BDEW says that “UBx” conditions have to be expanded just like packages: For example “UB1” shall be expanded to “([931] ∧ [932] [490]) ⊻ ([931] ∧ [933] [491])”.

This just doesn’t work out for multiple reasons:

1. Other than _all_ the other requirement constraints RC 490, 491, 492 and 493 are self-referencing. While “normal” RCs act like “You have to provide this (“Foo”) if the other thing (“Bar”) meets a requirement”, the 49x RCs are of kind “This (“Foo”) has to meet certain requirements (e.g. the end of a German day), regardless of the other things (“Bar”). So the usual requirement constraint evaluation approach (“Search for Bar and derive from there what it means for this (Foo)”) won’t work and is overly complicated, too. Also, if the pseudo requirement constraint 490-493 is UNFULFILLED, this does _not_ mean that the data must not be provided which is also a different behaviour compared to usual requirement constraints.

2. No one who understands the concept of datetime+offset and is able to parse datetime+offset nowadays cares, if you use (“x datetime” with an “0 offset”) or (“x+z datetime” that has a “z offset”) instead. It’s just BDEWs home-brewed EDIFACT serialization rule that, for no real reason, restricts us to set the offset z to “+00:00” always. https://imgflip.com/i/65giq5

AHBicht won’t restrict you to use datetime offset==”+00:00”. Because we don’t care and you should not care. The scope of AHBicht is to evaluate expressions and data, not to obey pointless BDEW EDIFACT rules. Also this default transformer won’t expand the UBx conditions into something which is overly complicated and in the end does really fit (for above reasons).

That being said… the thing that actually happens is: UBx will be replaced with a format constraint (plus a requirement constraint in case of UB3) that is fulfilled, if and only if the value provided obeys the original meaning of UBx. So the data provided will be evaluated just as you’d expect them to be evaluated but without all the bureaucracy.

Condition UB1 checks if the datetime provided is the (inclusive) start / (exclusive) end of a German “Stromtag”. Condition UB1 will be replaced with the format constraint 932.

Condition UB2 checks if the datetime provided is the (inclusive) start / (exclusive) end of a German “Gastag”. Condition UB2 will be replaced with the format constraint 934.

Condition UB3 checks if the datetime provided is the (inclusive) start / (exclusive) end of a German “Stromtag” if the receiver is from division electricity (RC 492) or a “Gastag” if a receiver is from division gas (RC 493). Condition UB3 will be replaced with two XOR connected format constraints, each of them coupled to a requirement constraint for the respective division.

time_condition(tokens: List[Token]) Tree[source]

try to resolve the package using the injected PackageResolver

async ahbicht.expressions.expression_resolver.expand_packages(parsed_tree: Tree) Tree[Token][source]

Replaces all the “short” packages in parser_tree with the respective “long” condition expressions

ahbicht.expressions.expression_resolver.expand_time_conditions(parsed_tree: Tree) Tree[Token][source]

Replaces all the time conditions “UBx” with format constraints (and requirements constraints for UB3)

async ahbicht.expressions.expression_resolver.parse_expression_including_unresolved_subexpressions(expression: str, resolve_packages: bool = False, replace_time_conditions: bool = True) Tree[Token][source]

Parses expressions and resolves its subexpressions, for example condition_expressions in ahb_expressions or packages in condition_expressions. :param expression: a syntactically valid ahb_expression or condition_expression :param resolve_packages: if true resolves also the packages in the condition_expressions :param replace_time_conditions: if true the time conditions “UBx” are replaced with format constraints

ahbicht.expressions.format_constraint_expression_evaluation module

This module evaluates the format constraint expression tree using EvaluatedFormatConstraints. The FormatConstraintTransformer defines the rules how the different parts and nodes of the format constraint expression tree are handled.

The used terms are defined in the README_conditions.md.

class ahbicht.expressions.format_constraint_expression_evaluation.FormatConstraintTransformer(input_values: Mapping[str, SupportedArgumentNode])[source]

Bases: BaseTransformer

Transformer that evaluates the trees built from the format constraint expressions. The input are the evaluated format constraint conditions in the form of EvaluatedFormatConstraints. The return value is an EvaluatedFormatConstraint whose attribute format_constraint_fulfilled describes whether the format constraint expression is fulfilled or not.

and_composition(left: EvaluatedFormatConstraint, right: EvaluatedFormatConstraint) EvaluatedFormatConstraint[source]

Evaluates logical and_composition

or_composition(left: EvaluatedFormatConstraint, right: EvaluatedFormatConstraint) EvaluatedFormatConstraint[source]

Evaluates logical (inclusive) or_composition

xor_composition(left: EvaluatedFormatConstraint, right: EvaluatedFormatConstraint) EvaluatedFormatConstraint[source]

Evaluates exclusive xor_composition

ahbicht.expressions.format_constraint_expression_evaluation.evaluate_format_constraint_tree(parsed_tree: Tree, input_values: Mapping[str, EvaluatedFormatConstraint]) EvaluatedFormatConstraint[source]

Evaluates the tree built from the format constraint expressions with the help of the FormatConstraintTransformer.

Parameters:
  • parsed_tree – Tree

  • input_values – dict(condition_key, EvaluatedFormatConstraint) :return: EvaluatedFormatConstraint

async ahbicht.expressions.format_constraint_expression_evaluation.format_constraint_evaluation(format_constraints_expression: str | None) FormatConstraintEvaluationResult[source]

Evaluation of the format constraint expression.

ahbicht.expressions.hints_provider module

Module to provide the condition hints from their respective json file as dictionary with the condition keys as keys and the hint texts as values.

class ahbicht.expressions.hints_provider.ContentEvaluationResultBasedHintsProvider[source]

Bases: HintsProvider

A hints provider that expects the evaluatable data to contain a ContentEvalutionResult as edifact seed. Other than the DictBasedHintsProvider the outcome is not dependent on the initialization but on the evaluatable data.

async get_hint_text(condition_key: str) str | None[source]

Get the hint text for the given condition key. :param condition_key: e.g. “501” :return: the corresponding hint text, e.g. “Data is thought to be interpreted as foo bar.”

class ahbicht.expressions.hints_provider.DictBasedHintsProvider(results: Mapping[str, str | None])[source]

Bases: HintsProvider

A Hints Provider that is based on hardcoded values from a dictionary

async get_hint_text(condition_key: str) str | None[source]

Get the hint text for the given condition key. :param condition_key: e.g. “501” :return: the corresponding hint text, e.g. “Data is thought to be interpreted as foo bar.”

class ahbicht.expressions.hints_provider.HintsProvider[source]

Bases: ABC

A Hints Provider provides plain text hints for a given condition number. This class provides the hints from the respective json file (defined by EdifactFormatVersion and EdifactFormat) as dictionary with the condition keys as keys and the hint texts as values.

edifact_format: EdifactFormat = NotImplementedError('The inheriting class needs to define a format to which it is applicable.')
edifact_format_version: EdifactFormatVersion = NotImplementedError('The inheriting class needs to define a format version.')
abstract async get_hint_text(condition_key: str) str | None[source]

Get the hint text for the given condition key. :param condition_key: e.g. “501” :return: the corresponding hint text, e.g. “Data is thought to be interpreted as foo bar.”

async get_hints(condition_keys: List[str], raise_key_error: bool = True) Dict[str, Hint][source]

Get Hints for given condition keys by asynchronously awaiting all self.get_hint_text at once

class ahbicht.expressions.hints_provider.JsonFileHintsProvider(edifact_format: EdifactFormat, edifact_format_version: EdifactFormatVersion, file_path: Path)[source]

Bases: DictBasedHintsProvider

The JsonFileHintsProvider loads hints from a JSON file.

ahbicht.expressions.package_expansion module

Package Expansion is the process of finding the condition expression which was abbreviated by using a package. e.g. if inside a tree “[123P]” is replaced by “[1] U ([2] O [3])”.

class ahbicht.expressions.package_expansion.ContentEvaluationResultBasedPackageResolver[source]

Bases: PackageResolver

A package resolver that expects the evaluatable data to contain a ContentEvalutionResult as edifact seed. Other than the DictBasedPackageResolver the outcome is not dependent on the initialization but on the evaluatable data.

async get_condition_expression(package_key: str) PackageKeyConditionExpressionMapping[source]

Returns a condition expression (e.g. “[1] U ([2] O [3])”) for the given package_key (e.g. “123P”) Returns None in the package_expression if the package is unresolvable (see ‘has_been_resolved_successfully’). :param package_key: The unique (integer) key of the package. The ‘P’ suffix is required. :return:

class ahbicht.expressions.package_expansion.DictBasedPackageResolver(results: Mapping[str, str | None])[source]

Bases: PackageResolver

A Package Resolver that is based on hardcoded values from a dictionary

async get_condition_expression(package_key: str) PackageKeyConditionExpressionMapping[source]

Returns a condition expression (e.g. “[1] U ([2] O [3])”) for the given package_key (e.g. “123P”) Returns None in the package_expression if the package is unresolvable (see ‘has_been_resolved_successfully’). :param package_key: The unique (integer) key of the package. The ‘P’ suffix is required. :return:

class ahbicht.expressions.package_expansion.JsonFilePackageResolver(edifact_format: EdifactFormat, edifact_format_version: EdifactFormatVersion, file_path: Path)[source]

Bases: DictBasedPackageResolver

The JsonFilePackageResolver loads package keys/expressions from a JSON file.

class ahbicht.expressions.package_expansion.PackageResolver[source]

Bases: ABC

A package resolver provides condition expressions for given package keys.

edifact_format: EdifactFormat = NotImplementedError('The inheriting package resolver needs to define a format to which it is applicable.')

the format for which the resolver may be used

edifact_format_version: EdifactFormatVersion = NotImplementedError('The inheriting package resolver needs to define a format version.')

the format version for which the resolver may be used

abstract async get_condition_expression(package_key: str) PackageKeyConditionExpressionMapping[source]

Returns a condition expression (e.g. “[1] U ([2] O [3])”) for the given package_key (e.g. “123P”) Returns None in the package_expression if the package is unresolvable (see ‘has_been_resolved_successfully’). :param package_key: The unique (integer) key of the package. The ‘P’ suffix is required. :return:

ahbicht.expressions.requirement_constraint_expression_evaluation module

This module evaluates the parsed condition expression tree regarding the requirement constraints using ConditionNodes. The RequirementConstraintTransformer defines the rules how the different parts and nodes of the condition expression tree are handled.

The used terms are defined in the README_conditions.md.

class ahbicht.expressions.requirement_constraint_expression_evaluation.RequirementConstraintTransformer(input_values: Mapping[str, SupportedArgumentNode])[source]

Bases: BaseTransformer

Transformer that evaluates the trees built from the condition expressions regarding the requirement constraints. The input are the conditions as defined in the AHBs in the form of ConditionNodes. In the case of a Bedingung/RequirementConstraint already evaluated for the single condition. Hints are evaluated as neutral element in the boolean logic: and_composition: True, or_composition: False.

After two nodes are evaluated in a composition, the resulting node has the node type EvalutatedComposition. The return value is a ConditionNode whose attribute conditions_fulfilled describes whether it is a required field, its hints are the gathered hints and its format_constraint_expression contains the gathered format constraints for the field in a newly built expression.

and_composition(left: RequirementConstraint | UnevaluatedFormatConstraint | Hint, right: RequirementConstraint | UnevaluatedFormatConstraint | Hint) EvaluatedComposition[source]

Evaluates logical and_composition

or_composition(left: ConditionNode, right: ConditionNode) EvaluatedComposition[source]

Evaluates logical (inclusive) or_composition

then_also_composition(left: Type[ConditionNode], right: Type[ConditionNode]) EvaluatedComposition[source]

A “then also” composition is typically used for format constraints. It connects an evaluable expression with a format constraint. If the conditions_fulfilled attribute evaluates to true, then also the attached format constraint has to be fulfilled.

xor_composition(left: ConditionNode, right: ConditionNode) EvaluatedComposition[source]

Evaluates exclusive xor_composition

ahbicht.expressions.requirement_constraint_expression_evaluation.evaluate_requirement_constraint_tree(parsed_tree: Tree, input_values: Mapping[str, RequirementConstraint | UnevaluatedFormatConstraint | Hint]) EvaluatedComposition[source]

Evaluates the tree built from the expressions with the help of the ConditionsTransformer.

Parameters:
  • parsed_tree – Tree

  • input_values – dict(condition_key, ConditionNode) :return: EvaluatedComposition

async ahbicht.expressions.requirement_constraint_expression_evaluation.requirement_constraint_evaluation(condition_expression: str | Tree) RequirementConstraintEvaluationResult[source]

Evaluation of the condition expression in regard to the requirement conditions (rc). The condition expression can either be a string that still needs to be parsed as condition expression or a tree that has already been parsed.

Module contents

instantiates a “global” logger for all parsing related stuff

exception ahbicht.expressions.InvalidExpressionError(error_message: str, invalid_expression: str | None = None)[source]

Bases: BaseException

Is raised when an expression is well-formed but invalid. A syntactical error leads to a SyntaxError during parsing with lark whereas this exception occurs during evaluation.