Learning pathsPricingChecking sign-in…
← ML curriculum

MLSD-026 · WORKED SYSTEM DESIGN

Feature platform

Design a governed feature platform with explicit event/availability time, compatible definitions, monotone online publication, bounded backfills and permission-aware historical replay. Prove the core contracts with independent temporal and numeric fixtures.

Author self-review; independent technical review pending. Pure synthetic temporal/projection/checkpoint/parity/generation calculations and independent SQLite oracle; no live store, stream processor, authorization service or model training.

Practice this design before reading →

Prerequisites and scoped previews

Events, identity and data contracts

Define keys, event/ingestion/availability times, schema evolution, dedupe and permitted use.

Feature engineering and transformations

Create numeric/categorical/text features, defaults and fitted transformations without leaking validation data.

Scoped prerequisite preview. The complete chapter is planned; this preview does not count as authored coverage.

Point-in-time joins and feature availability

Use both event-time and actual availability when reconstructing historical decisions.

Feature platforms and freshness contracts

Separate batch/stream/offline/online responsibilities and justify a feature store only when needed.

Training-serving consistency

Version feature/transform/model contracts and compare training versus serving behavior.

Observability and operational response

Separate system, data, model, product and decision-policy signals with owners and runbooks.

Scoped prerequisite preview. The complete chapter is planned; this preview does not count as authored coverage.

Governance, privacy, lineage and deletion

Trace permitted data use through snapshots, features, indexes and artifacts; define deletion obligations.

What, when, why and how

Immutable semantic feature contract

what
A feature is a versioned meaning: tenant/entity key, source/window, type/unit, transform, freshness, default, purpose and owner. A model-feature bundle orders these inputs for one compatible consumer.
when
Use this before building shared storage, publishing definitions or promoting models and schema changes.
why
A numeric field can change from count to rate without a type error. Registration alone neither validates sources nor guarantees serving availability.
how
Write examples and golden outputs, assign domain/platform/consumer owners and pin each request/export to immutable definitions. Change semantics under a new version and migrate an entire compatible bundle.

Serving replay and activation intervals

what
Event time describes a source fact; ingestion/validation/online activation describe when it became usable. An activation ledger records when a specific value was current.
when
Use it for point-in-time datasets, parity diagnostics, incident replay and delayed corrections.
why
An event-time-only historical join leaks late arrivals; a latest-only cache loses what an earlier request actually read. Offline availability and actual online activation can differ.
how
For authorized exact identity/generation, require event_time <= T and available_at <= T < superseded_at, with null end unbounded. Enforce nonoverlap and freshness at T. Label corrected-history exports separately and never fabricate old activation times.

Monotone projection and idempotency

what
A conditional projector accepts a newer source order in one namespace and treats identical event identities as retries. A durable activation/pointer change belongs in one atomic publication boundary.
when
Use this when stream delivery is at least once, producers correct events, old backfills finish late or stores are replicated.
why
Last-write-wins by arrival can replace a newer fact with an old one. A retried event must not change its original activation time or duplicate an aggregate contribution.
how
Validate identity/schema and current lifecycle authority; deduplicate immutable payloads, reject conflicts and compare event timestamp plus source revision sequence. Use transactional/CAS publication with an outbox/reconciliation strategy; the pure fixture models only deterministic decisions.

Bounded reproducible backfill

what
A backfill names immutable inputs/definition/transform, lifecycle generation, target namespace and bounded chunks with idempotent checkpoints.
when
Use this for new features, repaired inputs, historical dataset rebuilding and restoring materialized state.
why
Unlimited retries can double-publish output, overload serving or resurrect deleted data. Checkpoint progress alone does not prove all output effects committed.
how
Tie chunk digest/output publication to durable expected checkpoint state, reject conflicting retries and isolate quotas. Recheck current authority at publication. Retain immutable history; current projection still refuses older source order.

Parity and explicit degradation

what
Parity compares the same permitted decision inputs, source identities/statuses, versions and transforms before testing numeric closeness. Missing/stale/deleted are different states.
when
Use it for offline/online alignment, feature releases, score regressions and fallback design.
why
Shared code does not repair input availability skew. Equal scores can hide compensating errors, and returning zero for denied data bypasses the permission contract.
how
Use independent temporal/golden oracles and exact semantic checks. Allow declared numeric tolerance only after those pass. Return status/provenance; default missing/stale only where the consumer is trained/validated for it. Deleted/unauthorized paths produce no score.

Governance and lifecycle fencing

what
Current trusted tenant/purpose access and entity lifecycle generation govern reads, exports and writes. Lineage connects design contracts and observed jobs/artifacts.
when
Use this across caches, historical snapshots, backfill workers, deletion propagation and multi-team operation.
why
Tenant prefixes identify data but do not authorize it. A stale job or accessible historical export can recreate revoked values; a lineage graph alone cannot enforce a barrier.
how
Check scope before lookup and epoch at read/publication, invalidate derived paths and track owned acknowledgements. Use lineage to locate cleanup/rebuild targets and record unresolved retention/model-influence limits; do not promise universal unlearning.

Clarify the platform and the decision

We serve governed features to recommendation/ranking consumers and construct permitted historical datasets. The platform itself predicts no target: its labels are correctness/availability test outcomes, not click labels. A simple SQL/batch pipeline and cache are the baseline. Production databases, streaming infrastructure and authorization are described contracts; this repository executes bounded fixtures.

These six assumed answers define an interview scope. All rates, deadlines, IDs and values are original synthetic assumptions, not a vendor architecture or measured deployment.

QuestionAssumed answerDesign consequence
Who consumes features?Several models in multiple tenants; tenant context is authenticated.Batched versioned feature-set API; no caller-chosen tenant authority.
What freshness is required?Hourly batch suffices initially; one activity feature permits age <= 3,600s.Start batch; add streaming only if measured value justifies it.
Which time question matters?Reproduce actual inputs for past decisions within permitted retention.Successful activation ledger plus semantic/age checks, not event-time-only reconstruction.
What latency/scale?5,000 reads/s, 20 features/request, illustrative 20ms platform budget.Bound fan-out and load-test tails; these are design targets only.
What does missing data mean?Optional activity defaults to raw zero plus a status flag; required features may reject/degrade.Pin fallback in model bundle and test its quality.
What access lifecycle?Current tenant/purpose permission and epoch apply even to old datasets.Fence exports and delayed writers; track deletion propagation.

Change the design when the answer changes

Branch A: if batch freshness meets the use case, keep reviewed SQL over immutable source snapshots, schedule bounded materialization and retain sufficient activation evidence. Avoid a stream processor, distributed watermark state and multiple serving stores until there is a measured need.

Branch B: if immediate per-session context drives value, compute bounded permitted request-time inputs or introduce an incremental pipeline with declared windows, watermark/correction semantics and failure policy. Do not reuse an hourly feature under a seconds-fresh contract. If exact past serving visibility was never recorded, disclose the replay gap and offer separately named corrected-history analysis.

Define correctness before popularity

The platform objective is trustworthy reusable inputs at acceptable latency/freshness/cost. Success is not the number of registered features or a consumer AUC increase attributed without an experiment. Domain/model consumers still own predictive targets and product evaluation.

Primary evidence includes eligible replay source-ID agreement, contract violations, successful publication/read availability, freshness/default rates, tenant isolation and checkpoint/deletion tests. Count rejected/failed cases explicitly; a low-latency default response is not equivalent to a fresh measured value.

MeasureDenominator/contractGuardrail
Replay correctnessValid authorized golden decisions, exact source/status and transformReport unsupported history separately; never count it as correct.
Freshness coverageEligible required feature reads meeting age/coverageSlice by feature/version and tenant tier without exposing identities.
Availability/latencyEligible requests including timeouts/errors; p50/p95/p99Track cold cache, retry load and hot partitions.
CostBytes, scans, read/write work and replica/history retentionPer-tenant admission and backfill isolation.
GovernanceDeclared affected artifacts and acknowledged propagationContain access now; track slower cleanup separately.

Make the SQL and cache baseline usable

Define activity_v1 in reviewed SQL against an immutable permitted snapshot. Persist entity-qualified values with source/definition/transform and coverage timestamps. A scheduled job validates outputs and conditionally populates an online key/value cache. A batch retrieval call checks access/freshness and returns value/status/provenance.

This baseline already supports repeatable offline joins if timestamps and activation evidence are real. It lacks sub-hour updates, fine-grained stream corrections and automatic cross-team discovery. Add a registry when shared definitions/ownership become hard to manage; add streaming when quality/freshness evidence warrants its operational cost. A registry is metadata, not a running materializer.

Write the v1 definition and compatible bundle

Our scalar fixture is activity for tenant T1/entity U1, version v1, count unit, finite number, scale-10-v1 transform, raw default zero and maximum age 3,600 seconds. The illustrative consumer formula is 2*(raw/10)+1; it is fixed arithmetic, not a trained model. Here activity is the count of permitted successful actions in the trailing hour [coverage_end - 1 hour, coverage_end). The fixture consumes the already-computed count, with eventAt equal to coverage_end: F1 covers [08:00,09:00), F2 [08:30,09:30). Their counts are 10 and 40. Source input selection/dedup and range validation happen upstream; this fixture does not compute these windows.

A bundle orders required/optional features, definitions, transforms, defaults, model input schema and consuming release. A /100 transform or count-to-rate change is a breaking semantic v2 even if shape/type remain identical. Old/new namespaces may coexist only under explicit permitted support and cost limits.

Contract fieldWhat/whyHow used
IdentityTenant/entity type/id, immutable definition version, epochEvery cache key, read, job and dataset example.
MeaningSource/window/coverage, type/unit, deterministic transformValidation, backfill, goldens and consumer compatibility.
DegradationFreshness, missing/stale defaults, required/optionalReturn explicit status; consumer selects approved fallback.
GovernanceOwner, purpose, lifecycle/retention policyAdmission/read/export checks and incident handoff.

Validate producers before accepting effects

Ingest an envelope with event identity, source contract version, tenant/entity, epoch, event time, source revision sequence, payload and digest. Authenticate producers and derive trusted scope; validate field types, ranges, source clock bounds and definition compatibility. Quarantine malformed/conflicting records with reason counts and a bounded repair path.

An acknowledgement means durable accepted input, not online availability. Record ingestion, validation and successful activation separately. Deduplicate by semantic payload and stable event identity; a replay with reordered JSON keys is still the same effect. Conflicting payload under one event ID is an error, not an update. A real aggregate must deduplicate input contributions before counting.

The implemented projector receives only current state and one candidate. Its retry/conflict checks cover that current identity; a production producer/event ledger must preserve dedup identities across superseded events and validate retries before projection. The pure example does not claim full-stream deduplication or source authorization.

Define stream windows and corrections

For an aggregate, specify event-time window bounds, event eligibility, dedup identity and coverage clock. A watermark is a declared completeness/latency trade-off, not proof no later event exists. Bound retained state and define what happens to events beyond the allowed correction horizon.

Within the correction horizon, publish a new revision under source order and record its actual activation. Beyond it, route to audited repair/corrected-history generation or reject under policy; never silently backdate a serving interval. The implemented scalar fixture accepts already-computed feature values; it does not run a streaming window engine.

Walk the temporal contract with real boundaries

F1 has event 09:00, raw 10, actual online availability 09:01 and supersession 10:10. F2 has event 09:30, raw 40 and actual online availability 10:10 with no end. At 10:00, replay reads F1. At exactly 10:10, F1 is no longer active and F2 becomes active. At 10:15 read F2.

At 10:30 F2 age is exactly 60 minutes and remains valid under the inclusive convention. At 10:45 it is 75 minutes old: return stale/default raw zero plus F2 provenance. A tenant T2 row with value 999 is never eligible for T1. Overlapping active intervals are a contract error. A generation-1 historical record is ineligible after current authority moves to generation 2.

These are serving-state replay rules. Corrected history may choose corrected values under a separately declared cutoff/policy; give it another snapshot identity and do not call it exact replay. If invalid data once actually served, preserve permitted incident evidence and distinguish actual observations from a cleaned analytical reconstruction.

Express the join and index its access path

The independent SQLite oracle selects exact tenant/entity/definition/version/epoch, event_time <= :T, available_at <= :T and (:T < superseded_at OR superseded_at IS NULL). It rejects more than one active row and checks age relative to :T. The synthetic UTC text encoding is canonical and ordered; production timestamp types should avoid arbitrary timezone-string comparisons.

Index the compound identity with interval/event columns based on query plans and partition large historical joins by dataset/tenant/time. A temporal predicate alone is not an efficient all-pairs join. Prepartition candidate ranges, bound examples/features and report scan amplification. Apply current export authorization and deletion guards outside/alongside the temporal query; SQL chronology cannot authorize a caller.

SELECT * FROM available_value
WHERE tenant = :tenant AND entity = :entity
  AND definition = :definition AND version = :version AND epoch = :epoch
  AND event_at <= :at AND available_at <= :at
  AND (superseded_at IS NULL OR :at < superseded_at);
-- Require <= 1 active row; then evaluate age at :at.
-- Trusted current access/generation guards also apply.

Publish current values without arrival-order corruption

The pure projector compares source event time then revision sequence within tenant/entity/definition/version/epoch. An identical ID and payload is a no-op; a conflicting retry or equal source order with different identity is rejected. An older source order is retained offline but cannot replace current state or create a fictitious online activation.

In production, perform expected-pointer/generation validation, closure of the old active interval, insertion of the new activation and pointer change atomically where possible. If stores are separate, choose an authoritative commit log, durable outbox/idempotent projection and reconcile by commit version. A crash between cache write and interval logging otherwise breaks exact replay. Record actual acknowledgement/activation guarantees rather than promising cross-store atomicity.

The interval fixture assumes one coherent authoritative serving namespace. Replicas or caches may serve older values after authoritative activation; then this ledger alone reconstructs the authoritative view, not necessarily the exact request input. Record each decision’s returned source/commit versions and observation time, or enforce a compatible read fence, to replay the actual inputs. Measure and state replica/cache consistency and clock-order limits rather than treating wall-clock timestamps as a global transaction order.

Make read, export and write acknowledgements precise

POST /feature-sets/read accepts an authenticated entity context, approved bundle and bounded list, not arbitrary SQL. It returns request/bundle/definition IDs, values, status, source references, event/coverage/availability times, generation and server observation time. Pin one read snapshot where available; otherwise expose per-feature observation versions and do not claim a cross-store atomic vector.

POST /datasets creates a bounded asynchronous job over example timestamps and pinned feature contracts plus replay/corrected mode. Admission returns a job ID, not completed rows. Export delivery rechecks current permission; GET job status distinguishes admitted, running, ready, failed and revoked. Producer ACK means durable ingestion; materialization ACK means the specified publication committed. Retries carry stable IDs. Timeouts have ambiguous effects and must be resolved by idempotency/status, not a fresh request identity.

ConditionResponse behaviorConsumer obligation
Present and freshReturn measured scalar and source/versionUse compatible ordered transform.
Missing/stale optionalReturn declared default and reason/statusModel must support/monitor that status.
Required missing or deadline exceededExplicit unavailable/partial result per API contractUse validated baseline or fail/degrade with owner.
Unauthorized/deletedDeny/no usable value; no zero-risk scoreStop use, propagate containment and audit permitted metadata.

Backfill in bounded reproducible chunks

A backfill run pins input snapshot INPUT1, definition v1, transform scale-10-v1, target namespace, tenant/entity generation and expected checkpoint version. Each chunk names a stable ID, half-open row range, row count and content digest. BF1 starts cursor 0/version 1; chunk C1 covers [0,2), commits cursor 2/version 2, and an identical retry returns unchanged state.

A different digest under C1 is rejected; a new chunk starting from a stale cursor/version is rejected. Publication checks current authority even if the job was admitted earlier. Outputs plus checkpoint must commit atomically or use deterministic output keys and reconciliation, otherwise advancing the cursor can skip lost data. The pure fixture updates metadata only and does not write outputs or prove distributed exactly-once effects.

Backfills do not rewrite old activation intervals. Historical results go to a new snapshot; any current-value projection still obeys monotone source order. Bound chunk rows, scan bytes, parallelism, retries and tenant budget; isolate backfill pools from serving and include cancellation/partial-run cleanup.

Execute independent goldens before comparing scores

For raw 40 under scale-10-v1, transformed value is 4 and the fixed score is 9. Raw 10 gives score 3. The wrong /100 transform would give .4 and score 1.8, but semantic validation rejects that bundle before a numeric tolerance is consulted. Missing/stale default raw zero gives score 1 only under this declared optional-feature consumer. Deleted data returns null and cannot be scored.

Compare exact entity/version/generation, source ID, active interval/status, feature order and transform first. Then compare raw/transformed numbers under a scoped tolerance such as 1e-9 for this scalar fixture. Test empty/invalid numbers, missing, stale, late arrivals and old-generation paths. Pair sampling from shadow reads must align the same as-of question and access conditions.

This problem trains no model, estimates no AUC and runs no experiment. Consumer model training would pin dataset examples and split by decision time/entities with availability/label-maturity constraints from the relevant problem chapter. Platform correctness is necessary input evidence, not proof of product lift.

Use the entity model as an executable design conversation

The following logical schema separates definition/source, event and successful activation, online pointer, run/chunk, bundle, snapshot/example, observed lineage and deletion state. Every FK has a rendered parent/child relationship and cardinality. Globally opaque IDs identify rows; composite tenant/entity/definition/epoch constraints enforce compatible references beyond basic FK existence.

Scalar columns are a design representation; JSON fields have versioned validated schemas. Historical partitions and append logs may be physically different from the transactional pointer store. Choose storage/indexing after access patterns and consistency guarantees. The SQLite oracle models activation selection only; it does not instantiate this full production schema or any real database migration.

Budget serving, history and repair together

At 5,000 requests/s and 20 features, naive per-feature calls create 100,000 calls/s before retry amplification. Batching cuts round trips but keys/bytes/partitions still cost work. Assume a 20ms platform budget only as an interview target; measure queueing, cold-key misses, authentication and p99 under skew rather than adding mean component timings.

10M entities * 20 values * 8 bytes = 1.6GB raw scalar values (decimal). Keys, contract metadata, timestamps, indexes, replicas, history and old/new bundles add substantial overhead. A historical table retaining repeated activations can dominate current values. Estimate update rate * average bytes * retention and bound replay scan/output sizes.

If a repair reads 100M rows at a sustained measured 50k rows/s, ideal scan time is 2,000s (~33.3 minutes) before shuffle, validation, output and retries. These are hypothetical inputs. Benchmark producer skew/hot entities and per-tenant cost. Increasing workers can saturate the serving dependency; apply admission/pool isolation before scaling concurrency.

Roll out definitions and roll back compatible bundles

Validate schema/semantic goldens and independent temporal tests first. Dual-compute a v2 namespace under quotas, shadow aligned requests, compare source/status/transform and freshness, then promote a compatible model-feature bundle by controlled canary. Predeclare stop gates for contract failures, deletion leaks, stale/default spikes, latency and downstream quality.

Keep a permitted compatible old bundle and data namespace for rollback during an explicit support window. A v2 count-to-rate migration cannot point an old model at the new values. If old data is revoked or its source no longer exists, old-bundle rollback is unavailable: contain/degrade using an approved baseline and rebuild a compatible release. Never undo deletion or silently lower a required freshness policy to make rollback work.

Operate freshness and correctness with owners

Domain owners monitor source semantics/completeness and corrections; platform owners monitor ingestion lag, rejected conflicts, activation lag, projector/version divergence, checkpoint age, p99/default rates, tenant cost and deletion propagation; consumer owners validate model behavior under status/fallback changes. Tie alerts to an owned action rather than a dashboard count.

A freshness incident: producer stops, cache latency stays low, measured values age out, default rate rises. Identify affected definitions/bundles, contain with approved fallback, pause unsafe promotion, restore producer/materialization and validate replay without moving old activation timestamps backward. Backfill under quotas and document the quality impact/unknowns. A platform cannot fix this by retraining automatically on corrupted history.

Fence deletion and restrict historical exports

Authority for T1/U1 generation 1 advances to generation 2 with access revoked. Read/export paths deny/no-value immediately under that authority, even when old snapshots remain stored. A delayed generation-1 materializer or backfill chunk fails at publication. If the identity is legitimately recreated at generation 2, old generation-1 data is still ineligible. Cache keys include epoch and reads validate authority freshness according to the policy.

Use observed lineage to locate sources, offline partitions, exported examples, online pointers/caches and downstream consumers. Track owned acknowledgements for invalidation, access restriction, redaction/rebuild and remaining failures. Revocation containment, physical removal from supported artifacts and model-influence remediation are separate milestones. Define policy-specific retention, auth-cache revocation bounds and permitted audit metadata; a graph or source-row deletion alone proves none of these.

Review normal, boundary and failure traces

Normal: accepted F1 activates at 09:01, a 10:00 replay returns raw 10/score 3, F2 activates at 10:10, a 10:15 read returns raw 40/score 9. An identical producer retry does not move activation time. A late event from 09:15 is ignored for current projection.

Boundary: at 10:10 only F2 is active; at 10:30 its age equals 3,600s and is usable; at 10:45 it is stale/default. Empty entity yields missing/default only for the optional feature; cross-tenant access is denied before lookup. Two active rows signal a corrupt contract rather than an arbitrary winner.

Failure: C1 commits cursor 2/version 2 and loses its ACK; identical retry does not double-advance. Conflicting retry fails. A generation barrier advances while the worker is paused; its resumed old-epoch chunk fails even with a previously valid checkpoint. A wrong transform fails semantic validation before a plausible score can be returned.

Defend alternatives and the Staff boundary

Latest-only cache is cheap for current reads but insufficient for exact serving replay. Warehouse SQL is flexible for bounded offline datasets but expensive/unpredictable in a synchronous request path. A stream processor improves freshness only with added state/correction/operational costs. An external feature-store framework can implement selected contracts; test provider/version behavior rather than assuming its defaults solve your exact semantics.

Staff work aligns definition ownership, consumer migrations, tenant isolation, allowed retention/replay, cost allocation and incident handoffs across teams. Negotiate a supported contract matrix and evidence for adoption; feature count is not the objective. Search and bot detection remain future pilot chapters; unwritten prerequisite lessons are shown as scoped previews rather than falsely complete content.

Data model, schema and relationships

Seventeen logical entities distinguish semantic definitions, accepted source events, actual serving activation, checkpointed jobs, ordered consumers, historical examples and lifecycle propagation. Every FK is rendered with cardinality; required conceptual entities retain stable IDs.

Implementation boundary: Production design contract only. Independent SQLite instantiates a scalar activation ledger for temporal selection; JavaScript uses bounded in-memory records. No live registry, migrations, access provider, full persistence or stream service is installed.

These are proposed logical schemas with field contracts, not executable database migrations. PK identifies a row, FK references an existing parent, UK is a uniqueness rule. A composite PK identifies the combination. Nullable references are marked with ?. A foreign key protects identity; cross-row limits, timing and state transitions also require the transaction rules below.

Tenant: relationship map

Connectors name the relationship; multiplicities state parents per child and children per parent. 0..1 means optional, 1 required, 0..* any number. Self-links show two roles of the same entity.

Tenant relationshipstenant 1 to entity_key 0..*: Tenant reference. entity_key.tenant_id → tenant.id. tenant 1 to source_contract 0..*: Tenant reference. source_contract.tenant_id → tenant.id. tenant 1 to feature_definition 0..*: Tenant reference. feature_definition.tenant_id → tenant.id.Tenant reference1 parent · 0..* childrenEntity keyid [PK]tenant_id [FK]entity_typeTenant reference1 parent · 0..* childrenSource contractid [PK]tenant_id [FK]versionTenant reference1 parent · 0..* childrenFeature definitionid [PK]tenant_id [FK]source_contract_id [FK]Tenantid [PK]policy_versionquota
Tenant: relationship map

Connectors name the relationship; multiplicities state parents per child and children per parent. 0..1 means optional, 1 required, 0..* any number. Self-links show two roles of the same entity.

Tenant relationshipstenant 1 to feature_set_bundle 0..*: Tenant reference. feature_set_bundle.tenant_id → tenant.id. tenant 1 to dataset_snapshot 0..*: Tenant reference. dataset_snapshot.tenant_id → tenant.id. tenant 1 to access_policy 0..*: Tenant reference. access_policy.tenant_id → tenant.id.Tenant reference1 parent · 0..* childrenFeature-set bundleid [PK]tenant_id [FK]versionTenant reference1 parent · 0..* childrenDataset snapshotid [PK]tenant_id [FK]bundle_id [FK]Tenant reference1 parent · 0..* childrenAccess policyid [PK]tenant_id [FK]purposeTenantid [PK]policy_versionquota
Entity key: relationship map

Connectors name the relationship; multiplicities state parents per child and children per parent. 0..1 means optional, 1 required, 0..* any number. Self-links show two roles of the same entity.

Entity key relationshipsentity_key 1 to feature_event 0..*: Entity key reference. feature_event.entity_key_id → entity_key.id. entity_key 1 to materialization_run 0..*: Entity key reference. materialization_run.entity_key_id → entity_key.id. entity_key 1 to online_pointer 0..*: Entity key reference. online_pointer.entity_key_id → entity_key.id.Entity key reference1 parent · 0..* childrenFeature eventid [PK]entity_key_id [FK]feature_definition_id [FK]Entity key reference1 parent · 0..* childrenMaterialization runid [PK]feature_definition_id [FK]entity_key_id [FK]Entity key reference1 parent · 0..* childrenOnline pointerid [PK]entity_key_id [FK]feature_definition_id [FK]Entity keyid [PK]tenant_id [FK]entity_type
Entity key: relationship map

Connectors name the relationship; multiplicities state parents per child and children per parent. 0..1 means optional, 1 required, 0..* any number. Self-links show two roles of the same entity.

Entity key relationshipsentity_key 1 to dataset_example 0..*: Entity key reference. dataset_example.entity_key_id → entity_key.id. entity_key 1 to deletion_request 0..*: Entity key reference. deletion_request.entity_key_id → entity_key.id.Entity key reference1 parent · 0..* childrenDataset exampleid [PK]snapshot_id [FK]entity_key_id [FK]Entity key reference1 parent · 0..* childrenDeletion requestid [PK]entity_key_id [FK]new_epochEntity keyid [PK]tenant_id [FK]entity_type
Source contract: relationship map

Connectors name the relationship; multiplicities state parents per child and children per parent. 0..1 means optional, 1 required, 0..* any number. Self-links show two roles of the same entity.

Source contract relationshipssource_contract 1 to feature_definition 0..*: Source contract reference. feature_definition.source_contract_id → source_contract.id. source_contract 1 to feature_event 0..*: Source contract reference. feature_event.source_contract_id → source_contract.id. source_contract 1 to lineage 0..*: Source contract reference. lineage.source_contract_id → source_contract.id.Source contract reference1 parent · 0..* childrenFeature definitionid [PK]tenant_id [FK]source_contract_id [FK]Source contract reference1 parent · 0..* childrenFeature eventid [PK]entity_key_id [FK]feature_definition_id [FK]Source contract reference1 parent · 0..* childrenObserved lineageid [PK]run_id [FK]source_contract_id [FK]Source contractid [PK]tenant_id [FK]version
Feature definition: relationship map

Connectors name the relationship; multiplicities state parents per child and children per parent. 0..1 means optional, 1 required, 0..* any number. Self-links show two roles of the same entity.

Feature definition relationshipsfeature_definition 1 to feature_event 0..*: Feature definition reference. feature_event.feature_definition_id → feature_definition.id. feature_definition 1 to materialization_run 0..*: Feature definition reference. materialization_run.feature_definition_id → feature_definition.id. feature_definition 1 to online_pointer 0..*: Feature definition reference. online_pointer.feature_definition_id → feature_definition.id.Feature definition reference1 parent · 0..* childrenFeature eventid [PK]entity_key_id [FK]feature_definition_id [FK]Feature definition reference1 parent · 0..* childrenMaterialization runid [PK]feature_definition_id [FK]entity_key_id [FK]Feature definition reference1 parent · 0..* childrenOnline pointerid [PK]entity_key_id [FK]feature_definition_id [FK]Feature definitionid [PK]tenant_id [FK]source_contract_id [FK]
Feature definition: relationship map

Connectors name the relationship; multiplicities state parents per child and children per parent. 0..1 means optional, 1 required, 0..* any number. Self-links show two roles of the same entity.

Feature definition relationshipsfeature_definition 1 to bundle_member 0..*: Feature definition reference. bundle_member.feature_definition_id → feature_definition.id. feature_definition 1 to dataset_example 0..*: Feature definition reference. dataset_example.feature_definition_id → feature_definition.id.Feature definition reference1 parent · 0..* childrenBundle memberid [PK]bundle_id [FK]feature_definition_id [FK]Feature definition reference1 parent · 0..* childrenDataset exampleid [PK]snapshot_id [FK]entity_key_id [FK]Feature definitionid [PK]tenant_id [FK]source_contract_id [FK]
Feature event: relationship map

Connectors name the relationship; multiplicities state parents per child and children per parent. 0..1 means optional, 1 required, 0..* any number. Self-links show two roles of the same entity.

Feature event relationshipsfeature_event 1 to available_value 0..*: Feature event reference. available_value.feature_event_id → feature_event.id.Feature event reference1 parent · 0..* childrenAvailable valueid [PK]feature_event_id [FK]run_id [FK]Feature eventid [PK]entity_key_id [FK]feature_definition_id [FK]
Materialization run: relationship map

Connectors name the relationship; multiplicities state parents per child and children per parent. 0..1 means optional, 1 required, 0..* any number. Self-links show two roles of the same entity.

Materialization run relationshipsmaterialization_run 1 to backfill_chunk 0..*: Materialization run reference. backfill_chunk.run_id → materialization_run.id. materialization_run 1 to available_value 0..*: Materialization run reference. available_value.run_id → materialization_run.id. materialization_run 1 to dataset_snapshot 0..*: Materialization run reference. dataset_snapshot.run_id → materialization_run.id.Materialization run reference1 parent · 0..* childrenBackfill chunkid [PK]run_id [FK]chunk_keyMaterialization run reference1 parent · 0..* childrenAvailable valueid [PK]feature_event_id [FK]run_id [FK]Materialization run reference1 parent · 0..* childrenDataset snapshotid [PK]tenant_id [FK]bundle_id [FK]Materialization runid [PK]feature_definition_id [FK]entity_key_id [FK]
Materialization run: relationship map

Connectors name the relationship; multiplicities state parents per child and children per parent. 0..1 means optional, 1 required, 0..* any number. Self-links show two roles of the same entity.

Materialization run relationshipsmaterialization_run 1 to lineage 0..*: Materialization run reference. lineage.run_id → materialization_run.id.Materialization run reference1 parent · 0..* childrenObserved lineageid [PK]run_id [FK]source_contract_id [FK]Materialization runid [PK]feature_definition_id [FK]entity_key_id [FK]
Available value: relationship map

Connectors name the relationship; multiplicities state parents per child and children per parent. 0..1 means optional, 1 required, 0..* any number. Self-links show two roles of the same entity.

Available value relationshipsavailable_value 1 to online_pointer 0..*: Available value reference. online_pointer.available_value_id → available_value.id. available_value 0..1 to dataset_example 0..*: Available value reference. dataset_example.available_value_id → available_value.id. available_value 0..1 to lineage 0..*: Available value reference. lineage.available_value_id → available_value.id.Available value reference1 parent · 0..* childrenOnline pointerid [PK]entity_key_id [FK]feature_definition_id [FK]Available value reference0..1 parent · 0..* childrenDataset exampleid [PK]snapshot_id [FK]entity_key_id [FK]Available value reference0..1 parent · 0..* childrenObserved lineageid [PK]run_id [FK]source_contract_id [FK]Available valueid [PK]feature_event_id [FK]run_id [FK]
Feature-set bundle: relationship map

Connectors name the relationship; multiplicities state parents per child and children per parent. 0..1 means optional, 1 required, 0..* any number. Self-links show two roles of the same entity.

Feature-set bundle relationshipsfeature_set_bundle 1 to bundle_member 0..*: Feature-set bundle reference. bundle_member.bundle_id → feature_set_bundle.id. feature_set_bundle 1 to dataset_snapshot 0..*: Feature-set bundle reference. dataset_snapshot.bundle_id → feature_set_bundle.id.Feature-set bundle reference1 parent · 0..* childrenBundle memberid [PK]bundle_id [FK]feature_definition_id [FK]Feature-set bundle reference1 parent · 0..* childrenDataset snapshotid [PK]tenant_id [FK]bundle_id [FK]Feature-set bundleid [PK]tenant_id [FK]version
Dataset snapshot: relationship map

Connectors name the relationship; multiplicities state parents per child and children per parent. 0..1 means optional, 1 required, 0..* any number. Self-links show two roles of the same entity.

Dataset snapshot relationshipsdataset_snapshot 1 to dataset_example 0..*: Dataset snapshot reference. dataset_example.snapshot_id → dataset_snapshot.id. dataset_snapshot 0..1 to lineage 0..*: Dataset snapshot reference. lineage.snapshot_id → dataset_snapshot.id.Dataset snapshot reference1 parent · 0..* childrenDataset exampleid [PK]snapshot_id [FK]entity_key_id [FK]Dataset snapshot reference0..1 parent · 0..* childrenObserved lineageid [PK]run_id [FK]source_contract_id [FK]Dataset snapshotid [PK]tenant_id [FK]bundle_id [FK]
Deletion request: relationship map

Connectors name the relationship; multiplicities state parents per child and children per parent. 0..1 means optional, 1 required, 0..* any number. Self-links show two roles of the same entity.

Deletion request relationshipsdeletion_request 1 to deletion_ack 0..*: Deletion request reference. deletion_ack.request_id → deletion_request.id.Deletion request reference1 parent · 0..* childrenDeletion acknowledgementid [PK]request_id [FK]targetDeletion requestid [PK]entity_key_id [FK]new_epoch

Entity definitions and field contracts

Tenant

Authenticated resource and policy boundary.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
policy_versionstring · VALUECurrent policy/reference version.
quotajson · VALUEVersioned read/backfill admission settings.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • Caller identity determines authorized tenant/purpose; keys alone do not grant access.

Entity key

Tenant-scoped business identity and authoritative lifecycle.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
tenant_idopaque_id · FKOwner tenant. · tenant.id
entity_typestring · VALUEEntity namespace, for example user.
external_keystring · VALUEOpaque tenant-local entity key.
epochinteger · VALUEMonotonically advancing lifecycle generation.
stateenum · VALUEactive or revoked under authoritative policy.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • UNIQUE(tenant_id,entity_type,external_key).
  • Epoch/state validation is atomic with authority changes; old-epoch data is ineligible.

Source contract

Pin producer input semantics and ownership.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
tenant_idopaque_id · FKOwning tenant. · tenant.id
versionstring · VALUEImmutable source schema/semantics revision.
ownerstring · VALUEDomain producer contact/team.
schemajson · VALUEValidated payload, order and correction contract.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • UNIQUE(tenant_id,id,version); source order and conflict policy are explicit.

Feature definition

Immutable feature meaning and serving contract.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
tenant_idopaque_id · FKOwner tenant. · tenant.id
source_contract_idopaque_id · FKPermitted source contract. · source_contract.id
namestring · VALUEStable logical feature name.
versionstring · VALUEImmutable semantic version.
semanticsjson · VALUEEntity/window/unit/type/transform/default/age/purpose/owner schema.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • UNIQUE(tenant_id,name,version).
  • Meaning changes produce a new version; source tenant must match definition tenant.

Feature event

Accepted validated scalar input/revision before serving activation.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
entity_key_idopaque_id · FKTarget entity. · entity_key.id
feature_definition_idopaque_id · FKExact immutable definition. · feature_definition.id
source_contract_idopaque_id · FKObserved producer contract. · source_contract.id
event_timetimestamp · VALUEWhen the source fact occurred.
ingested_attimestamp · VALUEDurable ingestion time; not activation.
epochinteger · VALUEExpected lifecycle generation.
source_sequenceinteger · VALUERevision order at equal event time.
payload_digeststring · VALUECanonical immutable payload identity.
valuenumber · VALUEValidated raw scalar count in this fixture.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • UNIQUE(entity_key_id,feature_definition_id,id); same ID/different payload rejected.
  • All tenant/source/definition/epoch compatibility validated; raw acceptance does not imply online visibility.

Materialization run

Pinned batch/stream/backfill execution context.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
feature_definition_idopaque_id · FKTarget version. · feature_definition.id
entity_key_idopaque_id · FKOne-entity fixture; real jobs partition scoped entity ranges. · entity_key.id
epochinteger · VALUEAuthority generation at admitted scope.
input_snapshotstring · VALUEImmutable input/manifest reference.
transformstring · VALUEPinned transform/runtime reference.
checkpoint_versioninteger · VALUEExpected optimistic version.
cursorinteger · VALUECommitted bounded range end.
stateenum · VALUEadmitted/running/completed/failed/revoked.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • Input/definition/transform immutable for run; multi-entity jobs require per-entity current barriers.

Backfill chunk

Durable idempotent output/checkpoint boundary.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
run_idopaque_id · FKOwning run. · materialization_run.id
chunk_keystring · VALUEStable retry identity within run.
rangejson · VALUEHalf-open from/to and bounded row count.
digeststring · VALUEImmutable chunk/output digest.
committed_versioninteger · VALUEResulting checkpoint version.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • UNIQUE(run_id,chunk_key).
  • Range/digest conflicts reject; output and checkpoint atomic or deterministic/reconciled.

Available value

Successful activation interval and source lineage.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
feature_event_idopaque_id · FKExact validated source value. · feature_event.id
run_idopaque_id · FKPublishing run. · materialization_run.id
available_attimestamp · VALUEActual online activation under declared commit semantics.
superseded_attimestamp? · VALUEExclusive interval end; null means current.
publication_versioninteger · VALUEMonotone committed projection version.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • No overlapping active intervals for entity/definition/epoch namespace.
  • available_at >= event_time; superseded_at > available_at; rejected old events create no activation.
  • One logical activation per accepted event in this coherent namespace; physical replicas/caches need observed read versions or an explicit consistency fence for exact request replay.

Online pointer

Current committed activation reference.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
entity_key_idopaque_id · FKEntity partition. · entity_key.id
feature_definition_idopaque_id · FKVersioned feature namespace. · feature_definition.id
available_value_idopaque_id · FKCurrent activation. · available_value.id
epochinteger · VALUECurrent lifecycle namespace.
versioninteger · VALUECAS/commit token.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • UNIQUE(entity_key_id,feature_definition_id,epoch).
  • Pointer activation must match entity/definition/epoch; closure/new activation/pointer commit coherently.

Feature-set bundle

Compatible ordered consumer input release.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
tenant_idopaque_id · FKOwning tenant. · tenant.id
versionstring · VALUEImmutable bundle version.
consumer_releasestring · VALUEModel/policy artifact identity; illustrative here.
stateenum · VALUEcandidate/approved/retired.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • UNIQUE(tenant_id,id,version); approval checks source/transform/default and permitted purpose.

Bundle member

Ordered feature membership and fallback expectation.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
bundle_idopaque_id · FKConsuming bundle. · feature_set_bundle.id
feature_definition_idopaque_id · FKExact feature version. · feature_definition.id
positioninteger · VALUEModel input order.
requiredboolean · VALUERequired versus optional degradation.
transformstring · VALUEExpected transform; must match definition.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • UNIQUE(bundle_id,position); UNIQUE(bundle_id,feature_definition_id).
  • Tenant/purpose and semantic compatibility validated before promotion.

Dataset snapshot

Immutable named replay or corrected-history export.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
tenant_idopaque_id · FKAuthorized dataset scope. · tenant.id
bundle_idopaque_id · FKPinned ordered contracts. · feature_set_bundle.id
run_idopaque_id · FKProducing execution. · materialization_run.id
modeenum · VALUEserving_replay or corrected_history.
cutofftimestamp · VALUEDeclared known-at/input cutoff.
manifeststring · VALUEImmutable bounded artifact reference.
access_stateenum · VALUEactive/restricted/replaced.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • Snapshots never silently change mode/contents; current export authorization applies to old manifests.

Dataset example

Decision-time entity and selected feature evidence.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
snapshot_idopaque_id · FKSnapshot membership. · dataset_snapshot.id
entity_key_idopaque_id · FKExample entity. · entity_key.id
feature_definition_idopaque_id · FKChosen feature contract. · feature_definition.id
available_value_idopaque_id? · FKSelected source activation; absent for missing/default. · available_value.id
decision_attimestamp · VALUEAs-of decision time.
epochinteger · VALUELifecycle at authorized construction.
statusenum · VALUEpresent/missing/stale; deleted/denied not exported as usable value.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • UNIQUE(snapshot_id,entity_key_id,decision_at,feature_definition_id).
  • Nullable activation only for missing; stale retains source. Scope/time/status validated beyond FK existence.

Observed lineage

Record actual job inputs and outputs, distinct from intended dependencies.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
run_idopaque_id · FKObserved execution. · materialization_run.id
source_contract_idopaque_id · FKObserved input contract. · source_contract.id
snapshot_idopaque_id? · FKObserved snapshot output when present. · dataset_snapshot.id
available_value_idopaque_id? · FKObserved activation output when present. · available_value.id
observed_attimestamp · VALUEObservation commit time.
artifact_digeststring · VALUEPermitted minimal artifact provenance.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • At least one output reference; both allowed only when observed together.
  • References/tenant must match run; lineage is not an authorization or deletion guarantee.

Access policy

Trusted purpose/scoped rights version, not caller asserted flags.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
tenant_idopaque_id · FKPolicy boundary. · tenant.id
purposestring · VALUEApproved processing purpose.
versionstring · VALUEPolicy revision.
grantsjson · VALUEVersioned service/entity/feature scope and enforcement.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • Trusted evaluator enforces current policy before read/export/write; cache revocation bounds explicitly owned.

Deletion request

Revocation barrier and propagation scope.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
entity_key_idopaque_id · FKEntity to revoke. · entity_key.id
new_epochinteger · VALUEAuthoritative next generation.
requested_attimestamp · VALUEAccepted request time.
stateenum · VALUEcontained/propagating/completed_with_declared_limits/failed.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • Authority/state advance durably before old work can publish; repeated request identity is idempotent.

Deletion acknowledgement

Owned evidence for each declared downstream target.

FieldType / keyMeaning and reference
idopaque_id · PKGlobally unique immutable row identity.
request_idopaque_id · FKPropagation request. · deletion_request.id
targetstring · VALUEStore/cache/export/consumer target identity.
ownerstring · VALUEResponsible remediation team.
stateenum · VALUEpending/acknowledged/failed/unsupported_with_limit.
evidencestring · VALUEPermitted check/rebuild/invalidation reference.

Code mapping: Logical production design; opaque globally unique row ID, tenant-compatible references enforced by compound constraints/transaction validation. Not an installed migration.

  • UNIQUE(request_id,target); unresolved failures/unsupported influence are visible, not silently complete.

Relationship cardinalities and their reasons

Parent → childMultiplicityFK / why
tenant → entity_key

Tenant reference

1 parent per child; 0..* children per parententity_key.tenant_id → tenant.id

Each Entity key row references one tenant row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

tenant → source_contract

Tenant reference

1 parent per child; 0..* children per parentsource_contract.tenant_id → tenant.id

Each Source contract row references one tenant row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

tenant → feature_definition

Tenant reference

1 parent per child; 0..* children per parentfeature_definition.tenant_id → tenant.id

Each Feature definition row references one tenant row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

source_contract → feature_definition

Source contract reference

1 parent per child; 0..* children per parentfeature_definition.source_contract_id → source_contract.id

Each Feature definition row references one source_contract row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

entity_key → feature_event

Entity key reference

1 parent per child; 0..* children per parentfeature_event.entity_key_id → entity_key.id

Each Feature event row references one entity_key row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

feature_definition → feature_event

Feature definition reference

1 parent per child; 0..* children per parentfeature_event.feature_definition_id → feature_definition.id

Each Feature event row references one feature_definition row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

source_contract → feature_event

Source contract reference

1 parent per child; 0..* children per parentfeature_event.source_contract_id → source_contract.id

Each Feature event row references one source_contract row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

feature_definition → materialization_run

Feature definition reference

1 parent per child; 0..* children per parentmaterialization_run.feature_definition_id → feature_definition.id

Each Materialization run row references one feature_definition row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

entity_key → materialization_run

Entity key reference

1 parent per child; 0..* children per parentmaterialization_run.entity_key_id → entity_key.id

Each Materialization run row references one entity_key row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

materialization_run → backfill_chunk

Materialization run reference

1 parent per child; 0..* children per parentbackfill_chunk.run_id → materialization_run.id

Each Backfill chunk row references one materialization_run row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

feature_event → available_value

Feature event reference

1 parent per child; 0..* children per parentavailable_value.feature_event_id → feature_event.id

Each Available value row references one feature_event row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

materialization_run → available_value

Materialization run reference

1 parent per child; 0..* children per parentavailable_value.run_id → materialization_run.id

Each Available value row references one materialization_run row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

entity_key → online_pointer

Entity key reference

1 parent per child; 0..* children per parentonline_pointer.entity_key_id → entity_key.id

Each Online pointer row references one entity_key row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

feature_definition → online_pointer

Feature definition reference

1 parent per child; 0..* children per parentonline_pointer.feature_definition_id → feature_definition.id

Each Online pointer row references one feature_definition row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

available_value → online_pointer

Available value reference

1 parent per child; 0..* children per parentonline_pointer.available_value_id → available_value.id

Each Online pointer row references one available_value row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

tenant → feature_set_bundle

Tenant reference

1 parent per child; 0..* children per parentfeature_set_bundle.tenant_id → tenant.id

Each Feature-set bundle row references one tenant row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

feature_set_bundle → bundle_member

Feature-set bundle reference

1 parent per child; 0..* children per parentbundle_member.bundle_id → feature_set_bundle.id

Each Bundle member row references one feature_set_bundle row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

feature_definition → bundle_member

Feature definition reference

1 parent per child; 0..* children per parentbundle_member.feature_definition_id → feature_definition.id

Each Bundle member row references one feature_definition row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

tenant → dataset_snapshot

Tenant reference

1 parent per child; 0..* children per parentdataset_snapshot.tenant_id → tenant.id

Each Dataset snapshot row references one tenant row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

feature_set_bundle → dataset_snapshot

Feature-set bundle reference

1 parent per child; 0..* children per parentdataset_snapshot.bundle_id → feature_set_bundle.id

Each Dataset snapshot row references one feature_set_bundle row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

materialization_run → dataset_snapshot

Materialization run reference

1 parent per child; 0..* children per parentdataset_snapshot.run_id → materialization_run.id

Each Dataset snapshot row references one materialization_run row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

dataset_snapshot → dataset_example

Dataset snapshot reference

1 parent per child; 0..* children per parentdataset_example.snapshot_id → dataset_snapshot.id

Each Dataset example row references one dataset_snapshot row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

entity_key → dataset_example

Entity key reference

1 parent per child; 0..* children per parentdataset_example.entity_key_id → entity_key.id

Each Dataset example row references one entity_key row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

feature_definition → dataset_example

Feature definition reference

1 parent per child; 0..* children per parentdataset_example.feature_definition_id → feature_definition.id

Each Dataset example row references one feature_definition row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

available_value → dataset_example

Available value reference

0..1 parent per child; 0..* children per parentdataset_example.available_value_id → available_value.id

Each Dataset example row references zero or one available_value row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

materialization_run → lineage

Materialization run reference

1 parent per child; 0..* children per parentlineage.run_id → materialization_run.id

Each Observed lineage row references one materialization_run row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

source_contract → lineage

Source contract reference

1 parent per child; 0..* children per parentlineage.source_contract_id → source_contract.id

Each Observed lineage row references one source_contract row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

dataset_snapshot → lineage

Dataset snapshot reference

0..1 parent per child; 0..* children per parentlineage.snapshot_id → dataset_snapshot.id

Each Observed lineage row references zero or one dataset_snapshot row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

available_value → lineage

Available value reference

0..1 parent per child; 0..* children per parentlineage.available_value_id → available_value.id

Each Observed lineage row references zero or one available_value row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

tenant → access_policy

Tenant reference

1 parent per child; 0..* children per parentaccess_policy.tenant_id → tenant.id

Each Access policy row references one tenant row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

entity_key → deletion_request

Entity key reference

1 parent per child; 0..* children per parentdeletion_request.entity_key_id → entity_key.id

Each Deletion request row references one entity_key row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

deletion_request → deletion_ack

Deletion request reference

1 parent per child; 0..* children per parentdeletion_ack.request_id → deletion_request.id

Each Deletion acknowledgement row references one deletion_request row; a parent may have many historical children. Compound tenant/context and lifecycle checks also apply.

Transaction boundaries

  1. Atomically validate current authority/source order and commit activation interval closure, next activation and online pointer; otherwise publish from an authoritative log with idempotent outbox/reconciliation and explicit observation limits.
  2. Commit deterministic chunk outputs with expected checkpoint/version, or reconcile output keys before advancing; an identical chunk retry cannot repeat effects.
  3. Advance entity revocation/epoch as authoritative barrier; read/export and publication check current authority. Cleanup acknowledgements are separate tracked work.

Indexes and uniqueness

  1. UNIQUE tenant/entity type/external key; compound tenant-compatible references or equivalent validated transactional constraints throughout.
  2. Historical activation access path by entity/definition/epoch and interval/event columns; time partition/snapshot ranges for bounded joins.
  3. UNIQUE run/chunk identity and bundle/position; current pointer unique namespace; deletion request/target lookup.

Schema traps and failure cases

  1. No overlap or arrival-time winner: detect conflicting payload/source order, broken intervals and pointer/log divergence and stop unsafe publication.
  2. A lost ACK retries the same chunk/producer identity; stale checkpoint/generation cannot publish after revocation.
  3. Historical exports and old bundles are still subject to current permission and permitted retention; lineage does not prove removal of learned influence.

Trace the records through one operation

  1. Create immutable activity v1/source contract and T1/U1 epoch 1; F1/F2 source events validate independently of activation.
  2. F1 activates 09:01; F2 atomically supersedes it 10:10; the 10:00 dataset example references F1 and 10:15 references F2.
  3. Bundle pins scale-10-v1 and optional default; BF1/C1 commits once; generation 2 barrier rejects old-epoch retries and restricts affected exports.

Execute the feature correctness trace

Opaque synthetic scalar records. No running feature store, stream processor, database transaction or authorization provider is executed.

Feature step 1 of 5

Replay actual availability, then check age

10:00 selects F1, raw 10; 10:15 selects F2, raw 40. At 10:10 only F2 is active; at 10:30 age equals 60 minutes. At 10:45: stale, raw default 0 with source F2.

Diagrams and relationships

Event time and actual activation

Replay follows successful activation intervals, not a later event-time-only backfill.

Scroll horizontally on smaller screens, or enlarge the diagram.

Event time and actual activationReplay follows successful activation intervals, not a later event-time-only backfill. F1 event 09:00; active 09:01 to Decision 10:00 reads F1: interval + age. Decision 10:00 reads F1 to F2 event 09:30; active 10:10: late was unavailable. F2 event 09:30; active 10:10 to Decision 10:15 reads F2: actual activation.interval + agelate was unavailableactual activationF1 event 09:00; active 09:01Decision 10:00 reads F1F2 event 09:30; active 10:10Decision 10:15 reads F2
Event time and actual activationReplay follows successful activation intervals, not a later event-time-only backfill. F1 event 09:00; active 09:01 to Decision 10:00 reads F1: interval + age. Decision 10:00 reads F1 to F2 event 09:30; active 10:10: late was unavailable. F2 event 09:30; active 10:10 to Decision 10:15 reads F2: actual activation.interval + agelate was unavailableactual activationF1 event 09:00; active 09:01Decision 10:00 reads F1F2 event 09:30; active 10:10Decision 10:15 reads F2
Definition and observed lineage

A snapshot pins contracts; observed runs link actual inputs/outputs instead of assuming designed dependencies ran.

Scroll horizontally on smaller screens, or enlarge the diagram.

Definition and observed lineageA snapshot pins contracts; observed runs link actual inputs/outputs instead of assuming designed dependencies ran. Definition + source contract to Run + immutable input snapshot: validate versions. Run + immutable input snapshot to Activation + online pointer: conditional publish. Run + immutable input snapshot to Dataset snapshot + examples: as-of export. Dataset snapshot + examples to Observed lineage + bundle: record actual artifacts.validate versionsconditional publishas-of exportrecord actual artifactsDefinition + source contractRun + immutable input snapshotActivation + online pointerDataset snapshot + examplesObserved lineage + bundle
Definition and observed lineageA snapshot pins contracts; observed runs link actual inputs/outputs instead of assuming designed dependencies ran. Definition + source contract to Run + immutable input snapshot: validate versions. Run + immutable input snapshot to Activation + online pointer: conditional publish. Run + immutable input snapshot to Dataset snapshot + examples: as-of export. Dataset snapshot + examples to Observed lineage + bundle: record actual artifacts.validate versionsconditional publishas-of exportrecord actual artifactsDefinition + source contractRun + immutable input snapshotActivation + online pointerDataset snapshot + examplesObserved lineage + bundle
Offline export under a replay contract

Historical selection is bounded and current permission still controls delivery.

Scroll horizontally on smaller screens, or enlarge the diagram.

Offline export under a replay contractHistorical selection is bounded and current permission still controls delivery. Authorized example timestamps to Temporal join + freshness: scope + decision time. Pinned ledger + definitions to Temporal join + freshness: availability intervals. Temporal join + freshness to Snapshot validation + goldens: identity/status parity. Snapshot validation + goldens to Recheck access; deliver artifact: bounded export.scope + decision timeavailability intervalsidentity/status paritybounded exportAuthorized example timestampsPinned ledger + definitionsTemporal join + freshnessSnapshot validation + goldensRecheck access; deliver artifact
Offline export under a replay contractHistorical selection is bounded and current permission still controls delivery. Authorized example timestamps to Temporal join + freshness: scope + decision time. Pinned ledger + definitions to Temporal join + freshness: availability intervals. Temporal join + freshness to Snapshot validation + goldens: identity/status parity. Snapshot validation + goldens to Recheck access; deliver artifact: bounded export.scope + decision timeavailability intervalsidentity/status paritybounded exportAuthorized example timestampsPinned ledger + definitionsTemporal join + freshnessSnapshot validation + goldensRecheck access; deliver artifact
Online reads and monotone publication

Ingestion acknowledgement and online activation are distinct; current authority fences writes and reads.

Scroll horizontally on smaller screens, or enlarge the diagram.

Online reads and monotone publicationIngestion acknowledgement and online activation are distinct; current authority fences writes and reads. Producer validation + dedup to Current authority + projector: source order. Current authority + projector to Activation log + online state: atomic commit contract. Activation log + online state to Batched authorized bundle read: observation version. Batched authorized bundle read to Fresh / default / unavailable: status + age + deadline.source orderatomic commit contractobservation versionstatus + age + deadlineProducer validation + dedupCurrent authority + projectorActivation log + online stateBatched authorized bundle readFresh / default / unavailable
Online reads and monotone publicationIngestion acknowledgement and online activation are distinct; current authority fences writes and reads. Producer validation + dedup to Current authority + projector: source order. Current authority + projector to Activation log + online state: atomic commit contract. Activation log + online state to Batched authorized bundle read: observation version. Batched authorized bundle read to Fresh / default / unavailable: status + age + deadline.source orderatomic commit contractobservation versionstatus + age + deadlineProducer validation + dedupCurrent authority + projectorActivation log + online stateBatched authorized bundle readFresh / default / unavailable
Backfill retry and lifecycle recovery

A lost acknowledgement retries the same chunk; deletion invalidates old authority before publication.

Scroll horizontally on smaller screens, or enlarge the diagram.

Backfill retry and lifecycle recoveryA lost acknowledgement retries the same chunk; deletion invalidates old authority before publication. Pinned run + chunk C1 to Validate epoch + checkpoint: bounded range + digest. Validate epoch + checkpoint to Publish + checkpoint commit: expected version. Publish + checkpoint commit to Lost ACK: identical C1 retry: no duplicate advance. Validate epoch + checkpoint to Barrier changed: reject old job: generation mismatch.bounded range + digestexpected versionno duplicate advancegeneration mismatchPinned run + chunk C1Validate epoch + checkpointPublish + checkpoint commitLost ACK: identical C1 retryBarrier changed: reject old job
Backfill retry and lifecycle recoveryA lost acknowledgement retries the same chunk; deletion invalidates old authority before publication. Pinned run + chunk C1 to Validate epoch + checkpoint: bounded range + digest. Validate epoch + checkpoint to Publish + checkpoint commit: expected version. Publish + checkpoint commit to Lost ACK: identical C1 retry: no duplicate advance. Validate epoch + checkpoint to Barrier changed: reject old job: generation mismatch.bounded range + digestexpected versionno duplicate advancegeneration mismatchPinned run + chunk C1Validate epoch + checkpointPublish + checkpoint commitLost ACK: identical C1 retryBarrier changed: reject old job

Engineer, Senior and Staff follow-ups

These are teaching lenses. Each answer changes the scope of reasoning; they are not official employer leveling criteria.

Engineer: Why does the 10:00 join return F1 even though F2 happened at 09:30?

F2 was not actually readable until 10:10. Replay uses the activation interval, identity/generation and decision-time age; event time alone leaks the late value into a past decision.

Engineer: Does stale default zero equal an actual count of zero?

No. Preserve stale/missing status and provenance, and use the default only under the compatible optional-feature consumer. Deleted or unauthorized data yields no usable value and no score.

Senior: How do you recover after a chunk commits but its acknowledgement is lost?

Retry the same stable chunk ID/range/digest. An identical committed retry returns unchanged cursor/version; conflicting payload fails. Production output effects must commit with the checkpoint or use deterministic idempotent output plus reconciliation.

Senior: How do you prevent cache and replay-ledger disagreement?

Put activation/pointer history in one authoritative atomic boundary or use a durable commit log/outbox with idempotent projections, explicit observed versions and reconciliation. Never label a raw accepted event online-visible before successful publication.

Staff: Who owns a breaking feature migration across ten consuming teams?

Domain owners define meanings; platform owns supported version/materialization contracts and isolation; consumers validate model/default compatibility. Stage explicit dual namespaces, support windows, cost allocation, promotion/rollback evidence and deprecation with owners.

Staff: Can old models and snapshots always be restored after deletion?

No. Current authority and retention constrain rollback/replay. Contain access, reject old-generation publications and track artifact remediation. If an old permitted bundle/data path is unavailable, use an approved baseline or rebuild; never resurrect revoked data for operational convenience.

Practice and self-review

Your practice draft

Design a shared feature platform for 5,000 reads/s and 20 features/request. Specify the SQL/cache baseline, temporal and version contracts, APIs, schema, backfill checkpointing, parity goldens, deletion fencing and rollout. Work F1/F2 at each boundary and recover after a lost chunk acknowledgement.

Saved locally on this device. The worked answer does not score your draft. Existing lesson notes and completion are separate.

Progressive hints

Hint 1

Start with tenant/entity/version/epoch, event time versus actual activation and a declared freshness/default contract.

Hint 2

Pin input/transform/target versions; distinguish raw ingestion ACK, successful activation and committed chunk effects.

Hint 3

Use exact semantic parity before numeric tolerance; a compatible rollback cannot bypass current permission.

Reveal worked answer guidance

F1 is selected at 10:00; F2 at 10:10/10:15/10:30; 10:45 is stale/default. Scores are 3 for F1 and 9 for F2 under /10; wrong /100 is rejected despite producing a finite 1.8. C1 [0,2) advances once to cursor 2/version 2 and identical retry is unchanged. Current generation fences reads and publication, including historical exports; deleted/denied has no score. The complete design adds owned contracts, valid schema relationships, bounded resource work and compatible rollout rather than claiming a toy fixture is a running service.

Evidence to check in your answer

  • Engineer: coherent baseline, complete semantic definition, precise API/status and temporal boundary math.
  • Senior: conditional projection, bounded idempotent backfill, independent parity tests, schema/index/atomicity and failure recovery.
  • Staff: ownership, tenant resource/access boundaries, migration/retention/rollback constraints and cost evidence.
  • All levels: distinguish executed fixtures from production guarantees, independent review and consumer quality.

For each item, record Missing, Prompted, Independent or Adaptive evidence. Adaptive means you can revise the reasoning under a changed constraint. Reading completion and readiness are separate.

Sources and verification scope

Original synthetic examples and reference calculations. Sources support narrowly scoped background; they do not establish production performance or independent chapter review.

Rules of Machine Learning ↗ · Baseline/infrastructure and training-serving consistency principles; dated examples are not current architecture claims.

Feast point-in-time joins ↗ · Historical feature retrieval reference; actual availability/revision contracts still need explicit modeling.

NIST AI Risk Management Framework ↗ · Risk vocabulary and governance; not a certification or blanket legal-compliance guarantee.

Feast feature retrieval ↗ · Offline/online retrieval and contract vocabulary only. Original activation-interval fixture is platform-neutral; no Feast integration or provider/default guarantee.

OpenLineage object model ↗ · Job/run/dataset and observed lineage vocabulary only. No OpenLineage SDK, authorization or deletion guarantee is implemented.

Primary background links checked during authoring on 2026-10-19. Arithmetic, temporal eligibility, maturity and split reference functions are checked by the bounded local fixture suite. SQL is explanatory, not a migrated production query. No GPU, external dataset, model API or training job is required.