cadrumo.application.ledger.actions_import module¶
Ledger source import services for bucket-scoped transaction catalogues.
Provider rows arrive through the
ParsedLedgerRowProtocol port.
This module classifies them against a loaded TransactionCatalogue,
persists imported Transaction instances,
records LEDGER_TRANSACTION_IMPORTED bucket events, and returns
LedgerImportOperationResult or
LedgerSourceImportResult.
- class LedgerProviderID(*values)[source]¶
Bases:
StrEnumCanonical provider ID strings accepted by the ledger import dispatch.
- AUTO¶
- CSV¶
- OFX¶
- QFX¶
- XLSX¶
- EXCEL¶
- N26¶
- PDF¶
- PDF_N26¶
- evaluate_import_rows(*, bucket_id, catalogue, parsed_rows, currency_normalizer=None, occurred_at=None)[source]¶
Classify every parsed row as imported / skipped / likely-duplicate.
Each
ParsedLedgerRowProtocolcarries the magnitudeRawTransactionand the authoritativedirectionthe provider derived from the source sign at the parse boundary; this classifier never re-derives flow from a sign. Deduplication keys onderive_import_fingerprint()- a direction- and currency-qualified identity that is stable across both later edits of a transaction and a re-export of the same movement in a different file format. The import/skip verdict itself comes fromclassify_import_row(), which the--verifydiagnostics path consumes too, so the persisting path, the--dry-runpreview and the verify report all agree on what a row is.Core types:
TransactionCatalogue.- Return type:
_ImportRowPlan- Parameters:
bucket_id (str)
catalogue (TransactionCatalogue)
parsed_rows (tuple[ParsedLedgerRowProtocol, ...])
currency_normalizer (CurrencyNormalizationService | None)
occurred_at (datetime | None)
- import_ledger_transactions(*, bucket_id, parsed_rows, ports, transaction_repository, bucket_event_repository, actor='operator', source_command='aeat app ledger import', occurred_at=None, currency_normalizer=None, catalogue=None)[source]¶
Import provider rows into one bucket catalogue and emit events.
Each
ParsedLedgerRowProtocolcarries the magnitudeRawTransactionplus the authoritativedirectionthe provider derived at the parse boundary, so the import path never re-derives flow from a sign.catalogueis the bucket’s already-loaded catalogue when the caller read one to diagnose the source against; otherwise it is loaded here.Returns a
LedgerImportOperationResultsummarising the imported, skipped, and likely-duplicate transactions.Core types:
TransactionCatalogue.- Return type:
- Parameters:
bucket_id (str)
parsed_rows (Iterable[ParsedLedgerRowProtocol])
ports (LedgerImportPorts)
transaction_repository (TransactionCatalogueCoCommitWriterProtocol)
bucket_event_repository (BucketEventHistoryCoCommitWriterProtocol)
actor (str)
source_command (str)
occurred_at (datetime | None)
currency_normalizer (CurrencyNormalizationService | None)
catalogue (TransactionCatalogue | None)
- import_ledger_source(command, *, ports, transaction_repository=None, bucket_event_repository=None, currency_normalizer=None)[source]¶
Validate, ingest, and optionally persist one ledger source file.
Returns a
LedgerSourceImportResult.- Return type:
- Parameters:
command (LedgerSourceImportCommand)
ports (LedgerImportPorts)
transaction_repository (TransactionCatalogueCoCommitWriterProtocol | None)
bucket_event_repository (BucketEventHistoryCoCommitWriterProtocol | None)
currency_normalizer (CurrencyNormalizationService | None)
- apply_fx_conversion(raw, currency_normalizer)¶
Return
(fx_rate, value_in_eur, rate_source, rate_date_iso)for a raw row.EUR-native rows and non-EUR rows with no normalizer / a missing rate yield all
None, preserving the coupling invariant onTransaction.
- aggregate_ledger_import_results(results)[source]¶
Fold the per-file results of a directory import into one result.
import_ledger_source()produces one result per file, so a directory import holds several and the operator is owed a single answer. Summing them is a statement about what an import IS – which counts add, which references concatenate, and which fields may not differ between files – so it belongs beside the function that produces them rather than beside the command that happens to call it more than once.The invocation-wide fields are ASSERTED rather than assumed.
dry_run,verify,periodandbucket_iddescribe the invocation. Each source file has its own content-derivedimport_batch_idin persisted events; a folder with distinct batch ids has no single batch id to report.- Parameters:
results (
Sequence[LedgerSourceImportResult]) – The per-file results, in the order the files were read.- Return type:
- Returns:
One result whose counts are sums and whose reference tuples are the concatenation, in file order – including every file’s validation and source-verification report, which the fold previously dropped after the first.
- Raises:
TransactionValidationError – If
resultsis empty, or if the results disagree on a field that describes the invocation.
- IMPORTABLE_SOURCE_EXTENSIONS: Final[frozenset[str]]¶
The file kinds this product can read as a bank statement. It is a statement about ingestion capability, not about one surface’s argument parsing, so a second frontend importing a folder selects exactly the same files.
- plan_ledger_import_sources(path)[source]¶
Resolve one import target into the ordered files to read.
A file is itself; a directory is its importable children. The extension filter is what keeps a stray note or an exported PDF in the same folder from being handed to a statement parser, and refusing an empty directory matters because the alternative is an import that reports success having read nothing.
Order is
scan_directory()’s deterministic sort. That is load-bearing rather than incidental: several files fold into one aggregated result, and a filesystem-dependent order would make the same folder import differently on two machines.- Parameters:
path (
Path) – The file or directory the operator named.- Return type:
- Returns:
The files to import, in the order they will be read.
- Raises:
TransactionValidationError – When
pathis a directory holding no importable file.