dpmcore.services.ast_generator
Generate engine-ready validation scripts from DPM-XL expressions. The
resulting enriched_ast is keyed by the resolved module URI and
carries the AST, resolved release, per-validation severity, operands,
tables, preconditions, and dependency information.
The same script generation is exposed through the generate-script
CLI command and the /api/v1/scripts REST endpoint.
The service also exports a module’s calculations set –
calculations_for_module() and its companion
calculations_datapoints() – which is the
operations linked to the module version through OperationOutput,
rather than the validations scoped to it. That export is exposed through
the export-calculations CLI command.
ASTGeneratorService
- class dpmcore.services.ast_generator.ASTGeneratorService(session=None)[source]
Bases:
objectGenerate engine-ready validation scripts from DPM-XL expressions.
- __init__(session=None)[source]
Build the service, optionally bound to a SQLAlchemy
session.- Parameters:
session (Session | None)
- Return type:
None
- script(expressions, module_code, module_version, preconditions=None, severity=None, severities=None, release=None)[source]
Generate an engine-ready validations script.
- Parameters:
expressions (
List[Tuple[str,str]]) –[(expression, validation_code), ...].module_code (
str) – Code of the primary module (e.g."COREP_Con").module_version (
str) – Version of the primary module (e.g."2.0.1").preconditions (
Optional[List[Union[Tuple[str,List[str]],Dict[str,Any]]]]) – Optional list of precondition specs. Each entry is either a tuple(precondition_expression, [validation_codes])or a dict with keysexpressionandaffected_operations(optionalcodeandversion_idare also accepted). A precondition can guard many validation codes; a validation may have no precondition. Codes that end up infailed_operationsare stripped from the emittedaffected_operations, and a precondition left gating nothing is dropped entirely.severity (
Optional[str]) – Optional global default severity tag ("error","warning","info"). Defaults to"warning".severities (
Optional[Dict[str,str]]) – Optional per-validation override map{validation_code: severity}. Resolution per validation isseverities.get(code, severity_global). Unknown codes (not present inexpressions) raiseValueError.release (
Optional[str]) – Optional release code. When omitted, resolved to the latest release whose window contains the requestedModuleVersion. The resolved release is surfaced in thedpm_releaseblock and used for every downstream DB filter.
- Return type:
- Returns:
A dict with keys
success(bool),enriched_ast(the namespaced dict, orNoneon failure),error(str orNone), andfailed_operations(a{validation_code: error_message}map of expressions skipped due to semantic errors, or because their precondition cannot be evaluated by the engine). The namespaced dict mirrors the shape pydpm’sgenerate_validations_scriptproduces.
- script_from_db(expressions, operation_vids, mv, release_row, preconditions=None, severity=None, severities=None, from_submission_dates=None)[source]
Generate a DB-discovered module version’s validations script.
For each operation, its persisted
OperationNodetree is tried first (db_ast.build_ast_from_db()) — falling back to re-parsing its expression text only when that isn’t possible (an unsupported construct, or the reshaper for it not being implemented yet — see dpmcore#364). Shares_process_operation()/_assemble_script()withscript(); the only thing that differs between the two is how each operation’sast_dict/parameters/ts/root_operator_idare obtained.- Parameters:
operation_vids (
Dict[str,int]) –{code: OperationVID}, from_discover_module_validations()— which operations have a persisted AST to try first.mv (
Any) – already resolved by the caller (script_for_module()), so this doesn’t re-resolve it.release_row (
Any) – already resolved by the caller (script_for_module()), so this doesn’t re-resolve it.preconditions (
Optional[List[Union[Tuple[str,List[str]],Dict[str,Any]]]]) – same asscript().from_submission_dates (
Optional[Dict[str,str]]) –{code: FromSubmissionDate}, from_discover_module_validations()— the real per-operation submission date. A code missing here (the column was null) falls back to_build_operation_entry()’s own default, same asscript()’s caller-supplied expressions.
- Return type:
- Returns:
Same shape as
script(). Unlikescript(), a per-operation scope-calculation error does not fail the whole result: it is recorded infailed_operationsand that operation is left out, the same as a semantic error or an ungateable precondition.script()still aborts on a scope error (#122) — this method discovers every active validation for the module itself, so one bad operation failing the whole discovered set would be a worse surprise here than for a caller-suppliedexpressionslist.
- script_for_module(module_code, module_version, release=None)[source]
Auto-discover a module version’s active validations and script them.
No
expressions,preconditionsorseveritiesneed to be supplied — they are looked up fromOperationScope/OperationScopeComposition/OperationVersionfor this module version, then handed toscript_from_db().
- calculations_for_module(module_code, reference_date, publication_date=None)[source]
Export a module version’s calculations set.
Where
script_for_module()scripts a module’s validations, this exports its calculations: the operations linked to the module version throughOperationOutput, parsed as one script, reordered so a calculation follows the ones it consumes, and serialized with every operand resolved to its datapoints.The companion datapoint map is
calculations_datapoints(); the two are computed by the same pass, so a caller that wants both should usecalculations_export()and read the two fields off it.- Parameters:
module_code (
str) – Code of the module (e.g."KRI").reference_date (
str) – Reference date,YYYY-MM-DD. The module version whose reference-date window contains it is the one exported; exactly one must.publication_date (
Optional[str]) – Publication date stamped into thedpm_releaseblock; defaults to today.
- Return type:
- Returns:
The export, keyed by the module’s EBA taxonomy URI.
- Raises:
ValueError – If the service has no database session.
DpmCoreError – If the module version, its calculations or the
OperationOutputtable cannot be resolved.
- calculations_datapoints(module_code, reference_date, publication_date=None)[source]
Map every datapoint a module’s calculations touch to its cell.
The companion of
calculations_for_module(), with the same arguments and the same failure modes.- Parameters:
- Return type:
- Returns:
{variable_id: {"table", "row", "column", "sheet"}}.- Raises:
ValueError – If the service has no database session.
DpmCoreError – If the module version, its calculations or the
OperationOutputtable cannot be resolved.
- calculations_export(module_code, reference_date, publication_date=None)[source]
Export a module’s calculations and datapoint map in one pass.
- Parameters:
- Return type:
- Returns:
Both halves of the export.
- Raises:
ValueError – If the service has no database session.
DpmCoreError – If the module version, its calculations or the
OperationOutputtable cannot be resolved.
- list_module_versions(module_code=None, release=None)[source]
Enumerate
(module_code, version_number)pairs to sweep.Used by the CLI’s
--all-modules/--all-versionssweep to discover targets forscript_for_module().- Parameters:
- Return type:
- Returns:
(module_code, version_number)pairs, ordered by(code, start_release_id), excluding ghost/phantomModuleVersionrows (from_reference_date == to_reference_date, both non-null — the same test_walk_ghost_chain()uses). Withrelease, a module whose only covering versions are ghosts is represented by its ghost fallback instead of being dropped (#372, see_ghost_fallback_versions()).- Raises:
ValueError – If a database session is missing, or
releasedoesn’t match anyRelease.code.
Calculations export
- class dpmcore.services.calculations_export.CalculationsExport(calculations, datapoints)[source]
A module version’s exported calculations and its datapoint map.
- calculations
The export, keyed by the module’s EBA taxonomy URI.
- datapoints
{variable_id: {table, row, column, sheet}}for every datapoint the calculations touch – the companion file the deployment reads alongside the export.
- class dpmcore.services.calculations_export.CalculationsExporter(session)[source]
Exports a module version’s calculations set.
- Parameters:
session (
Session) – An open SQLAlchemy session.
- __init__(session)[source]
Bind the exporter to
session.- Parameters:
session (Session)
- Return type:
None
- export(module_code, reference_date, publication_date=None)[source]
Export
module_code’s calculations as ofreference_date.- Parameters:
- Return type:
- Returns:
The export and its datapoint map.
- Raises:
ConfigurationError – If the database has no
OperationOutputtable.NotFound – If the module version, or its calculations, cannot be resolved.
Invalid – If the parsed script does not have one statement per calculation.
SemanticError –
6-4if the calculations form a cycle, or6-1if two of them assign the same output.