rfgen.admission_estimation

rfgen.admission_estimation is the sealed, offline boundary for deterministic cloud-admission estimates. It accepts already-resolved configuration, signed pricing evidence, and a short-lived quota snapshot; it neither contacts a provider nor creates resources. Every public V1 model is a frozen, strict Pydantic model: unknown fields are forbidden and instances are immutable.

Closed enums

Enum

Values

CloudProvider

AWS, GCP, AZURE

PriceUnit

VCPU_HOUR, GPU_HOUR, GB_MONTH, REQUEST, GB_EGRESS, TOKEN

QuotaUnit

VCPU, GPU, CONCURRENT_REQUEST, CONCURRENT_JOB, GB

StorageBillingMode

BILLABLE, LOCAL_NONBILLABLE

LocalNonbillableReason

LOCAL_PATH, CALLER_OWNED_STORAGE

QuotaValidationCode

MISSING_QUOTA, STALE_QUOTA, INSUFFICIENT_QUOTA, QUOTA_UNIT_MISMATCH

MissingInputReason

UNKNOWN_SKU, UNKNOWN_REGION, MISSING_FX, STALE_PRICE, STALE_FX, MISSING_QUOTA, STALE_QUOTA, INSUFFICIENT_QUOTA

CostEstimateStatus

COMPLETE, UNKNOWN_PRICE, STALE_PRICE, UNKNOWN_QUOTA

Common field rules

All listed timestamps are timezone-aware UTC datetime values. A digest is a lowercase 64-hex-character SHA-256 string. A currency is an uppercase ISO 4217 code. Text fields described as nonblank are stripped and must remain nonempty. QuantityIntervalV1 is the common nonnegative interval:

class QuantityIntervalV1(BaseModel):
    low: Decimal
    expected: Decimal
    high: Decimal

Each endpoint must be finite and 0 <= low <= expected <= high.

Price evidence

TierV1

start: Decimal, end: Decimal | None = None, and unit_price: Decimal. start, end when present, and unit_price are finite and nonnegative; an end must be greater than start.

PriceSnapshotV1

Field

Type

Default

provider

CloudProvider

required

sku, region, source_uri, api_revision

str

required

currency

str

required

unit

PriceUnit

required

tiers

tuple[TierV1, ...]

required

observed_at

datetime

required

source_sha256, row_sha256

str

required

The text fields are nonblank; currency follows the common currency rule. tiers is nonempty, begins at zero, and has contiguous, non-overlapping ranges. row_sha256 is a self-hash over this row’s RFC 8785 canonical JSON with row_sha256 omitted.

FXSnapshotV1

Field

Type

Default

base

Literal["EUR"]

required

quote

str

required

rate

Decimal

required

reference_date

date

required

source_sha256, row_sha256

str

required

quote is an ISO 4217 currency and rate is finite and positive. row_sha256 is this row’s canonical self-hash.

PricingBundleV1

Field

Type

Default

schema_version

Literal[1]

required

prices

tuple[PriceSnapshotV1, ...]

required

fx

tuple[FXSnapshotV1, ...]

required

target_currency

str

required

created_at, expires_at

datetime

required

bundle_sha256

str

required

Price rows must be uniquely sorted by (provider, sku, region, unit) and FX rows by quote. expires_at is after created_at; bundle_sha256 is the canonical self-hash for the bundle.

Planning and provenance

ExecutorAdmissionPlanV1

executor_selector: str, provider: CloudProvider, region: str, duration_hours: QuantityIntervalV1, vcpu_count: QuantityIntervalV1, vcpu_sku: str, vcpu_quota_name: str, vcpu_quota_unit: Literal[QuotaUnit.VCPU], gpu_count: QuantityIntervalV1, gpu_sku: str | None = None, gpu_quota_name: str | None = None, and gpu_quota_unit: Literal[QuotaUnit.GPU] | None = None. The selector, region, and VCPU identity fields are nonblank. The three GPU identity fields are either all absent or all present.

AnnotationAdmissionPlanV1

orchestrator_selector: str, provider: CloudProvider, region: str, requests: QuantityIntervalV1, request_sku: str, input_tokens: QuantityIntervalV1, output_tokens: QuantityIntervalV1, token_sku: str, quota_name: str | None = None, quota_required: Decimal | None = None, and quota_unit: QuotaUnit | None = None. The selector, region, and SKU fields are nonblank. The three quota fields are either all absent or all present; a present requirement is finite and nonnegative.

StorageAdmissionPlanV1

Field

Type

Default

backend_selector, path_scheme

str

required

billing_mode

StorageBillingMode

required

provider

`CloudProvider

None`

region

`str

None`

stored_gb, retention_months, egress_gb

QuantityIntervalV1

required

retention_hours

`QuantityIntervalV1

None`

storage_sku, egress_sku

`str

None`

nonbillable_reason

`LocalNonbillableReason

None`

The selector and scheme are nonblank. BILLABLE requires provider, region, both SKUs, and no nonbillable reason; recognized schemes bind to providers: gs→GCP, s3→AWS, and az, abfs, abfss, or azure→AZURE. LOCAL_NONBILLABLE requires file or local, no billing identity, zero egress, and a reason. If supplied, every retention_months endpoint equals the corresponding retention_hours / Decimal(730) endpoint.

AdmissionPlanningConfigV1

record_count: int (strictly greater than zero), executor: ExecutorAdmissionPlanV1, storage: StorageAdmissionPlanV1, and annotation: AnnotationAdmissionPlanV1 | None = None.

ResolvedPluginV1 and PluginLockV1

ResolvedPluginV1 has group: str, name: str, distribution: str, version: packaging.version.Version, wheel_sha256: str, and billing_provider: CloudProvider | None = None. The three names are nonblank, the version must parse as Version (and serializes as a string), and the wheel digest follows the common digest rule.

PluginLockV1 has schema_version: Literal[1], plugins: tuple[ResolvedPluginV1, ...], and lock_sha256: str. Plugins are uniquely sorted by (group, name) and lock_sha256 is a canonical self-hash.

ResolvedConfigProvenanceV1

generation_config_sha256: str, executor_config_sha256: str, storage_config_sha256: str, annotation_config_sha256: str | None = None, hydra_resolved_sha256: str, plugin_lock_sha256: str, source_revision: str, and resolved_at: datetime. Each non-null hash follows the common digest rule. source_revision is a lowercase 40-hex Git SHA. This model has no self-hash: it is embedded in the self-hashed resource spec.

AdmissionResourceSpecV1

schema_version: Literal[1], run_id: str, record_count: int (>0), executor_selector: str, storage_backend_selector: str, annotation_orchestrator_selector: str | None = None, planning: AdmissionPlanningConfigV1, provenance: ResolvedConfigProvenanceV1, and spec_sha256: str. The selectors are nonblank when present. The count and selectors must equal their planning counterparts, the annotation selector must match the optional annotation plan, and spec_sha256 is the canonical self-hash.

Construction and resource mapping

build_admission_resource_spec

build_admission_resource_spec(
    resolved_cfg: DictConfig,
    planning: AdmissionPlanningConfigV1,
    *,
    plugin_lock: PluginLockV1,
    source_revision: str,
    resolved_at: datetime,
) -> AdmissionResourceSpecV1

The only configuration ingress. It resolves DictConfig interpolations and strictly validates generation, executor, storage, and optional annotation configuration. It requires planning identity to match that resolved configuration, uses recognized storage-scheme bindings, and for an unknown billable scheme requires the matching rfgen.stores lock entry’s billing_provider. It derives the provenance hashes and spec_sha256.

AdmissionInputError(code="CONFIG_MISMATCH") identifies divergent valid inputs. AdmissionInputError(code="PROVENANCE") identifies unresolved or malformed configuration, lock, revision, or construction evidence.

ResourceDemandV1 and NonbillableResourceV1

ResourceDemandV1 fields are component: str, provider: CloudProvider, sku: str, region: str, quantity: QuantityIntervalV1, unit: PriceUnit, quota_name: str | None = None, quota_required: Decimal | None = None, quota_unit: QuotaUnit | None = None, and source_fields: tuple[str, ...]. Text fields are nonblank, source_fields is nonempty/nonblank, and the three quota fields are all absent or all present; a requirement is finite and nonnegative.

NonbillableResourceV1 fields are component: str, unit: PriceUnit, quantity: QuantityIntervalV1, backend_selector: str, path_scheme: str, reason: LocalNonbillableReason, and source_fields: tuple[str, ...]. Its text/source-field rules are the same. Neither mapping-result model has a self-hash; both are embedded in CostEstimateV1.

map_admission_resource_spec

map_admission_resource_spec(
    spec: AdmissionResourceSpecV1,
) -> tuple[tuple[ResourceDemandV1, ...], tuple[NonbillableResourceV1, ...]]

Returns sorted billable demands and separately sorted local nonbillable rows. It multiplies nonnegative interval endpoints for VCPU/GPU hours and storage GB-months, adds annotation token endpoints, and uses the 730-hour retention conversion when hours were supplied. It does not infer missing identities.

Quota and estimate output

QuotaRowV1 and QuotaSnapshotV1

QuotaRowV1 has provider: CloudProvider, region: str, quota_name: str, unit: QuotaUnit, limit: Decimal, used: Decimal, source_uri: str, api_revision: str, observed_at: datetime, and row_sha256: str. Its text fields are nonblank, amounts are finite/nonnegative with used <= limit, and row_sha256 is a canonical self-hash.

QuotaSnapshotV1 has schema_version: Literal[1], rows: tuple[QuotaRowV1, ...], created_at: datetime, expires_at: datetime, and snapshot_sha256: str. Rows are uniquely sorted by (provider, region, quota_name, unit); expiry is after creation and within one hour; the snapshot digest is a canonical self-hash.

Cost models

CostLineItemV1 fields are component: str, provider: CloudProvider, sku: str, region: str, quantity: QuantityIntervalV1, unit: PriceUnit, tiers_sha256: str, price_source_sha256: str, fx_source_sha256: str | None = None, low: Decimal, expected: Decimal, high: Decimal, and assumption: Literal["EXACT", "BOUNDED"]. Text and present digests follow the common rules; costs are finite/nonnegative and ordered. It has no self-hash.

MissingCostInputV1 fields are provider: CloudProvider, sku: str | None = None, region: str, unit: PriceUnit | None = None, quota_name: str | None = None, and reason: MissingInputReason. It contains exactly one identity: price (sku and unit, no quota name) or quota (quota name, no SKU/unit). It has no self-hash.

UnitCostTotalV1 fields are unit: PriceUnit, low: Decimal, expected: Decimal, high: Decimal, line_item_count: int, and total_sha256: str. Amounts are finite/nonnegative; its digest is the SHA-256 of unit_total_projection(...), so it is a self-hashing total. The projection requires a positive non-boolean int, ordered finite amounts, and returns exactly unit, low, expected, high, and line_item_count, with canonical decimal strings.

unit_total_projection(
    unit: PriceUnit,
    low: Decimal,
    expected: Decimal,
    high: Decimal,
    line_item_count: int,
) -> dict[str, str | int]

CostEstimateV1 fields are schema_version: Literal[1], spec_sha256: str, bundle_sha256: str, currency: str, line_items: tuple[CostLineItemV1, ...], unit_totals: tuple[UnitCostTotalV1, ...], nonbillable: tuple[NonbillableResourceV1, ...], missing: tuple[MissingCostInputV1, ...], low_total: Decimal, expected_total: Decimal, high_total: Decimal, status: CostEstimateStatus, and estimate_sha256: str. It requires sorted, unique line-item identities; exactly one sorted unit total for every priced unit; exact unit and currency sums; ordered finite totals; and COMPLETE iff missing is empty. estimate_sha256 is its canonical self-hash.

Verification protocol and estimate

PricingVerificationAdapter

class PricingVerificationAdapter(Protocol):
    def verify(
        self,
        bundle: Bundle,
        *,
        policy: AttestationPolicyV1,
        predicate_model: type[PricingBundleV1],
    ) -> Any: ...

The caller injects this narrow verification seam; it owns trust roots, identity policy, network transport, and Sigstore configuration. A Layer 14 SigstoreDSSEAdapter implements the compatible verification surface. No default adapter exists.

estimate

estimate(
    spec: AdmissionResourceSpecV1,
    snapshot: PricingBundleV1,
    *,
    quota: QuotaSnapshotV1,
    pricing_bundle: Bundle,
    pricing_policy: AttestationPolicyV1,
    adapter: PricingVerificationAdapter,
    as_of: datetime,
    deadline_monotonic_s: float,
) -> CostEstimateV1

Authenticates the exact PRICING_V1 pricing predicate, bundle digest, subject name pricing-bundle.json, and canonical snapshot before resource mapping. It performs exact provider/SKU/region/unit lookups, forbids quota-unit conversion, integrates price tiers endpoint by endpoint, and converts FX endpoints independently. Price evidence is stale after 24 hours, FX after seven days, and quota after one hour. Missing/stale price, FX, or quota is returned as typed missing input and a non-COMPLETE status; no substitute estimate is made. The finite monotonic deadline is checked throughout.

Error contract

Error

Stable meaning

AdmissionInputError

Input proof failed; code is CONFIG_MISMATCH or PROVENANCE.

PricingIntegrityError

Pricing evidence or as_of integrity failed.

PricingConflictError

Price or FX identity rows are duplicate or unsorted.

QuotaIntegrityError

Quota integrity failed; its code is a QuotaValidationCode.

PricingSignatureError

DSSE verification, returned statement, subject, predicate, or payload binding failed.

AdmissionDeadlineError

The monotonic deadline elapsed before an estimate was emitted.

See also

  • Cloud Backends gives the operational workflow and provider-scheme rules.

  • Attestation documents the closed DSSE verification adapter.