aeat.domain.user_profile._portable_export module

Portable-export bundle for cross-bucket user-profile transfer.

This module is isolated from domain.user_profile._values so the four heavy domain types it composes (CalculationRevision, WorkUnit, Transaction, ModeloRecord) and their transitive registry-parse cost do not enter sys.modules at user-profile package init. The UserProfileRecord is included via the profile field of UserProfilePortableExport. This module is the canonical definition site; domain.user_profile exposes the same class through lazy __getattr__ resolution so package import stays light.

class CarriedSecureObject(**data)[source]

Bases: BaseModel

One decrypted secure-object row carried by a v3 bundle.

A bundle addresses each carried row by its natural object key (the store-derived identifier), never by the stored HMAC lookup digest: the digest is keyed by the per-bucket data-encryption key, so a source-bucket digest is unreadable in the recipient bucket (proven by the custody roundtrip tests). On import the carried payload is re-saved through the owning store’s save path, which re-derives the natural key under the recipient DEK and re-encrypts. The natural object_key is carried for coverage auditing and for the bespoke stores that re-save through the raw secure-object substrate.

payload_b64 is the canonical adapter-serialised form: for typed stores it is the Envelope JSON bytes the store persists, and for the attachment-blob store it is the raw decrypted blob bytes (which are not JSON). The owning store adapter is the sole interpreter of these bytes. classification carries the row’s SensitivityClass so import replays the same namespace sensitivity contract.

Parameters:
namespace: str
object_key: str
classification: SensitivityClass
schema_version: int
written_at: datetime
payload_b64: str
property payload: bytes

Return the decrypted payload bytes carried by the bundle.

class CoverageManifest(**data)[source]

Bases: BaseModel

Namespace coverage declared by a portable-export bundle.

Parameters:
custody_profile: Literal['structured', 'full']
carried_namespaces: tuple[str, ...]
excluded_namespaces: tuple[str, ...]
row_counts_by_namespace: Mapping[str, int]
class UserProfilePortableExport(**data)[source]

Bases: BaseModel

User-directed portable profile export payload.

bundle_schema_version gates forward-compatible import: callers that read an export bundle compare this integer to their supported range before attempting to parse profile. Increment it when the serialised shape changes in a backward-incompatible way.

Version 3 is the only supported shape (this is a pre-beta project with no released bundles; earlier shapes are deleted, not bridged — see no-legacy-compatibility). It carries profile plus the financial-history fields work_units, ledger_transactions, calculation_revisions, and filing_records. It also declares the v3 generic secure-object carry surface and coverage manifest; those fields default empty until the transport-aware serialise/deserialise phases populate them.

Encrypted-material blobs are NOT included (ADR D2: strip encrypted material; re-encrypt under recipient bucket DEK on import).

Parameters:
bundle_schema_version: int
exported_at: datetime
profile: UserProfileRecord
work_units: tuple[_WorkUnit, ...]
ledger_transactions: tuple[_Transaction, ...]
calculation_revisions: tuple[_CalculationRevision, ...]
filing_records: tuple[_ModeloRecord, ...]
carried_objects: tuple[CarriedSecureObject, ...]
coverage_manifest: CoverageManifest