docs/adr/ADR-0008-feature-view-versioning.md
Accepted
When a feature view's schema changed in Feast, the old definition was silently overwritten. This created several problems:
Add automatic version tracking to Feast feature views. Every time feast apply detects a schema or UDF change, a versioned snapshot is saved to the registry.
version="v2" on a feature view replaces the active definition with the v2 snapshot.@v<N> syntax (e.g., driver_stats@v2:trips_today) for reading from a specific version.Only schema and UDF changes create new versions:
Metadata-only changes (description, tags, owner, TTL) update the active definition in place without creating a version.
Version history tracking is lightweight registry metadata (serialized proto snapshots). There is no performance cost to the online path. Every feast apply that changes a feature view will:
feast feature-views list-versions <name> to list history.registry.list_feature_view_versions(name, project) programmatically.registry.get_feature_view_by_version(name, project, version_number).Version-qualified reads from separate online store tables are gated behind a config flag:
registry:
path: data/registry.db
enable_online_feature_view_versioning: true
When enabled, driver_stats@v2:trips_today reads from a version-specific table (project_driver_stats_v2). When disabled (default), using @v<N> refs raises a clear error.
driver_stats = FeatureView(
name="driver_stats",
entities=[driver],
schema=[...],
source=my_source,
version="v2", # revert to v2's definition
)
Safety: The user's definition (minus the version field) must match the currently active definition. If both schema and version pin are changed, feast apply raises FeatureViewPinConflict.
--no-promote)The --no-promote flag saves a version snapshot without updating the active definition, enabling phased rollouts:
# Stage the new version
feast apply --no-promote
# Populate the v2 online table
feast materialize --views driver_stats --version v2 ...
# Migrate consumers one at a time (using @v2 refs)
# Promote v2 as the default
feast apply
Each version's data lives in its own online store table. By default, feast materialize targets the active version. A --version flag targets specific versions:
feast materialize --views driver_stats --version v1 2024-01-01T00:00:00 2024-01-15T00:00:00
(feature_view_name, project_id, version_number) with retry logic for auto-increment races.get_historical_features are not supported.sdk/python/feast/feature_view.py (version fields), docs/adr/feature-view-versioning.md