Component relationships
Provider identity and changing source formats
Provider adapters discover items and attachments through a shared protocol. Native identity and content fingerprints distinguish repeated fetches from new revisions. Original artifacts and document versions are retained before extraction.
Fixed column mappings are brittle when schemas and layouts change. Extraction produces a common typed JSON draft; structure parsing and business validation remain separate so uncertain or incomplete fields can be reviewed.
Durable execution and per-file recovery
Persisted jobs separate source discovery, preparation and extraction. A worker owns scheduling, progress, cancellation, retry and bounded parallel extraction. Processing a batch does not erase completed drafts or retained publications when one file fails.
The interface reads source/item states and run records. Active-file names, completed/total counts and concurrency expose ongoing work; failed runs retain their recovery context.
Validation and publication contract
The same typed forecast structure covers extraction, correction and validation. Missing references, invalid dates/quantities and duplicate rows remain visible for correction. Zero is distinct from missing data; whole-piece quantities are not silently rounded.
Approval locks and revalidates the submission, persists published lines and records the decision plus any superseded approval. Rejected records and prior approvals remain available. Unlocking archives the publication before a new analysis.
Normalized output and snapshot comparison
Published rows can be read as the latest approved version per file or as historical snapshots. Filtered reads preserve organization scope. A directional comparison identifies additions, removals and changed line values between selected publications.
The interface supports filtered CSV/XLSX exports and configured SQL delivery. Export and delivery consume published data; draft corrections do not silently change historical values.
Software paradigm
A React client calls FastAPI services. Pydantic models define the JSON boundary; SQLAlchemy entities retain sources, runs, source revisions, submissions and decisions. Provider objects implement discovery protocols, while service functions orchestrate processing and publication.