• Русский
  • Быстрый старт

    Эта страница посвящена пользовательскому ресурсу FeatureStore, который является основным интерфейсом для развертывания и настройки Feast после установки оператора.

    Предварительные требования

    • Feast Operator установлен. См. Install Feast.
    • Для примеров с PVC в кластере должен быть задан StorageClass по умолчанию, либо целевое значение storageClassName должно быть известно заранее.
    • Для внешних backend вместо файлового хранилища на основе PVC заранее подготовьте необходимые службы:
      • Рекомендуется PostgreSQL 16. PostgreSQL используется для SQL registry и, при необходимости, для PostgreSQL online store.
      • Рекомендуется Redis 6.0 или более поздняя версия. Redis используется для Redis online store. Feast поддерживает один экземпляр Redis, Redis Cluster и Redis Sentinel.
      • Подготовьте Kubernetes Secrets, содержащие параметры подключения к backend, до того, как на них будут ссылаться из CR FeatureStore.

    Для примеров PostgreSQL и Redis на этой странице предполагается, что backend service, база данных или schema, учетные данные и Kubernetes Secrets уже существуют. Тем не менее, в целевом кластере все равно следует проверить сетевую доступность и совместимость драйверов.

    Обзор CR FeatureStore

    Наиболее часто используемые поля в CR FeatureStore:

    ПолеНазначениеТипичное использование
    spec.feastProjectИмя проекта FeastОбязательно. Используется для организации определений feature и метаданных.
    spec.feastProjectDirСпособ создания репозитория featureИспользуйте стандартный feast init, шаблон инициализации или Git-репозиторий.
    spec.services.offlineStoreКонфигурация offline storeХранение исторических данных и необязательный удаленный offline server.
    spec.services.onlineStoreКонфигурация online storeНизколатентное чтение online feature.
    spec.services.registryКонфигурация registryХранение метаданных для entities, feature views, feature services и разрешений.
    spec.services.uiUI serviceВключение Feast UI.
    spec.authzКонфигурация авторизацииОбычно роли на основе Kubernetes или управление доступом на основе OIDC.
    spec.replicasРеплики PodОставьте 1 для простых развертываний. Для нескольких реплик используйте устойчивое хранилище.

    Общая конфигурация services

    Offline Store

    offlineStore управляет тем, где хранятся исторические данные feature и будет ли доступен удаленный offline server.

    Основные варианты:

    • persistence.file: файловое хранилище, обычно DuckDB на PVC, подходит для локальной разработки и оценки
    • persistence.store: внешний offline backend, например BigQuery или другой поддерживаемый Feast offline store
    • server: {}: создает Service удаленного offline server для сетевого доступа

    Пример DuckDB на PVC:

    services:
      offlineStore:
        persistence:
          file:
            type: duckdb
            pvc:
              create:
                storageClassName: fast
                resources:
                  requests:
                    storage: 10Gi
              mountPath: /data/offline
        server: {}

    Пример на основе store:

    services:
      offlineStore:
        persistence:
          store:
            type: bigquery
            secretRef:
              name: feast-data-stores
        server: {}

    Online Store

    onlineStore используется для низколатентного предоставления feature.

    Основные варианты:

    • persistence.file: локальное файловое хранилище, обычно только для разработки
    • persistence.store: Redis, PostgreSQL или другой поддерживаемый Feast backend для online store
    • server: необязательные дополнительные настройки сервера, такие как env, envFrom, resources, tls или volumeMounts

    Рекомендуемые версии backend для примеров на этой странице:

    • Redis 6.0 или более поздняя версия
    • PostgreSQL 16

    Пример с файлом на PVC:

    services:
      onlineStore:
        persistence:
          file:
            path: online_store.db
            pvc:
              create:
                resources:
                  requests:
                    storage: 5Gi
              mountPath: /data/online

    Пример на Redis:

    services:
      onlineStore:
        persistence:
          store:
            type: redis
            secretRef:
              name: feast-data-stores

    Пример на PostgreSQL:

    services:
      onlineStore:
        persistence:
          store:
            type: postgres
            secretRef:
              name: feast-data-stores
        server:
          envFrom:
            - secretRef:
                name: postgres-secret

    Registry

    registry хранит метаданные Feast. Он может быть локальным для текущего FeatureStore или повторно использовать удаленный registry.

    Основные варианты:

    • registry.local.persistence.file: файловый registry на PVC или в object storage
    • registry.local.persistence.store: registry на основе SQL
    • registry.local.server: {}: предоставляет registry server для удаленного доступа
    • registry.remote: повторно использует registry из другого FeatureStore или внешний hostname

    Для примеров registry на основе SQL на этой странице рекомендуется PostgreSQL 16.

    Пример registry на PVC:

    services:
      registry:
        local:
          persistence:
            file:
              path: registry.db
              pvc:
                create:
                  resources:
                    requests:
                      storage: 5Gi
                mountPath: /data/registry
          server: {}

    Пример registry на SQL:

    services:
      registry:
        local:
          persistence:
            store:
              type: sql
              secretRef:
                name: feast-data-stores
          server: {}

    Пример с удаленным registry:

    services:
      registry:
        remote:
          feastRef:
            name: <shared-featurestore-name>
            namespace: <shared-namespace>

    UI

    Чтобы включить Feast UI, задайте:

    services:
      ui: {}

    Без ui: {} Service UI не создается.

    Типовые шаблоны persistence

    Конфигурация на основе PVC

    Это самый простой шаблон для оценки, локального тестирования и развертываний с одной репликой:

    apiVersion: feast.dev/v1
    kind: FeatureStore
    metadata:
      name: <featurestore-name>
      namespace: <namespace>
    spec:
      feastProject: <feast-project>
      replicas: 1
      services:
        offlineStore:
          persistence:
            file:
              type: duckdb
              pvc:
                create:
                  resources:
                    requests:
                      storage: 10Gi
                mountPath: /data/offline
          server: {}
        onlineStore:
          persistence:
            file:
              path: online_store.db
              pvc:
                create:
                  resources:
                    requests:
                      storage: 5Gi
                mountPath: /data/online
        registry:
          local:
            persistence:
              file:
                path: registry.db
                pvc:
                  create:
                    resources:
                      requests:
                        storage: 5Gi
                  mountPath: /data/registry
            server: {}
        ui: {}

    Redis Online Store + SQL Registry

    Это распространенный шаблон для устойчивого online store и registry на базе базы данных.

    Сначала создайте Secret:

    apiVersion: v1
    kind: Secret
    metadata:
      name: feast-data-stores
      namespace: <namespace>
    type: Opaque
    stringData:
      redis: |
        connection_string: redis.<namespace>.svc.cluster.local:6379,password=<redis-password>
      sql: |
        path: postgresql+psycopg://<user>:<password>@postgres.<namespace>.svc.cluster.local:5432/feast
        cache_ttl_seconds: 60
        sqlalchemy_config_kwargs:
          pool_pre_ping: true
          echo: false

    Затем укажите на него в FeatureStore:

    apiVersion: feast.dev/v1
    kind: FeatureStore
    metadata:
      name: <featurestore-name>
      namespace: <namespace>
    spec:
      feastProject: <feast-project>
      services:
        offlineStore:
          persistence:
            file:
              type: duckdb
              pvc:
                create: {}
                mountPath: /data/offline
          server: {}
        onlineStore:
          persistence:
            store:
              type: redis
              secretRef:
                name: feast-data-stores
        registry:
          local:
            persistence:
              store:
                type: sql
                secretRef:
                  name: feast-data-stores
            server: {}
        ui: {}

    PostgreSQL Online Store + SQL Registry

    Для PostgreSQL в качестве backend online store Secret может содержать как postgres, так и sql записи:

    apiVersion: v1
    kind: Secret
    metadata:
      name: feast-data-stores
      namespace: <namespace>
    type: Opaque
    stringData:
      postgres: |
        host: postgres.<namespace>.svc.cluster.local
        port: 5432
        database: feast
        db_schema: public
        user: <user>
        password: <password>
      sql: |
        path: postgresql+psycopg://<user>:<password>@postgres.<namespace>.svc.cluster.local:5432/feast
        cache_ttl_seconds: 60
        sqlalchemy_config_kwargs:
          pool_pre_ping: true
          echo: false

    Затем используйте:

    services:
      onlineStore:
        persistence:
          store:
            type: postgres
            secretRef:
              name: feast-data-stores
      registry:
        local:
          persistence:
            store:
              type: sql
              secretRef:
                name: feast-data-stores
          server: {}

    Registry в Object Storage

    Файл registry также можно разместить в S3 или GCS:

    services:
      registry:
        local:
          persistence:
            file:
              path: s3://bucket/registry.db
              cache_ttl_seconds: 60
              cache_mode: sync

    Примечания по Secrets

    Когда используется persistence.store, оператор считывает параметры backend из Kubernetes Secret.

    Важные моменты:

    • по умолчанию имя ключа Secret совпадает с настроенным type
    • для type: redis оператор читает ключ redis
    • для type: postgres оператор читает ключ postgres
    • для type: sql оператор читает ключ sql
    • при необходимости имя ключа можно переопределить с помощью secretKeyName

    Содержимое Secret должно соответствовать стилю конфигурации backend, используемому в feature_store.yaml, но без самого поля type backend.

    Инициализация Feature Repository

    Оператор может инициализировать feature repository тремя распространенными способами.

    Инициализация по умолчанию

    Если spec.feastProjectDir не задан, оператор выполняет стандартный feast init <project> и создает repository по пути:

    <offline mount path>/<feastProject>/feature_repo

    Init Template

    Шаблон инициализации можно использовать, когда оператор должен развернуть определенный шаблон Feast:

    spec:
      feastProject: <feast-project>
      feastProjectDir:
        init:
          template: spark

    Git Repository

    Git можно использовать, если определения feature уже хранятся в системе контроля версий:

    spec:
      feastProject: <feast-project>
      feastProjectDir:
        git:
          url: https://github.com/feast-dev/feast-credit-score-local-tutorial
          ref: 598a270

    Если feature repository расположен не в стандартном подкаталоге feature_repo, задайте featureRepoPath.

    Развертывание FeatureStore

    Примените пример на основе PVC:

    kubectl apply -f featurestore.yaml

    Основное поле готовности — status.phase. Когда развертывание готово, это поле принимает значение Ready.

    Проверить его напрямую можно так:

    kubectl get featurestore <featurestore-name> -n <namespace> -o jsonpath='{.status.phase}'

    Services и доступ

    Оператор записывает информацию о подключении в status FeatureStore:

    kubectl get featurestore <featurestore-name> -n <namespace> -o jsonpath='{.status.serviceHostnames}'
    kubectl get featurestore <featurestore-name> -n <namespace> -o jsonpath='{.status.clientConfigMap}'

    Оператор создает имена Service по шаблону feast-<featurestore-name>-<component>. Распространенные примеры:

    • feast-<featurestore-name>-online
    • feast-<featurestore-name>-offline
    • feast-<featurestore-name>-registry
    • feast-<featurestore-name>-ui

    Сгенерированный clientConfigMap содержит клиентский feature_store.yaml для текущего развертывания FeatureStore. Конфигурация хранится под ключом feature_store.yaml и может быть напрямую загружена клиентами Feast, включая Python-приложения и задания внутри кластера.

    Типовые способы доступа:

    • использовать сгенерированные имена Service внутри кластера
    • использовать сгенерированный client ConfigMap как конфигурацию клиента Feast
    • публиковать Services через метод доступа, используемый в целевой среде

    Если требуется сетевой доступ к offline server или registry server, в CR следует задать offlineStore.server: {} или registry.local.server: {}.

    Использование Feast SDK и CLI

    Определения feature обычно хранятся вне workload FeatureStore, в локальном repository, Git repository, CI job или другом workflow на основе SDK. Сгенерированный клиентский feature_store.yaml используется для подключения Feast CLI или Python SDK к развернутым службам.

    Когда feast apply запускается из клиентской среды, registry service должен быть доступен из Feast client. Для локального режима registry, используемого на этой странице, задайте:

    services:
      registry:
        local:
          server: {}

    Если также требуется удаленная materialization или удаленное получение historical data, откройте и offline server:

    services:
      offlineStore:
        server: {}

    Структура repository

    Подготовьте feature repository в окружении Feast client и поместите в этот repository сгенерированную клиентскую конфигурацию как feature_store.yaml. Конфигурация может быть прочитана из ConfigMap, имя которого указано в .status.clientConfigMap.

    Пример структуры repository:

    <feature-repo>/
      feature_store.yaml
      driver_repo.py
      data/

    Корень repository — это каталог, содержащий feature_store.yaml.

    Один и тот же корень repository используется как Feast CLI, так и Python SDK. Для кода Python загрузите его так:

    from feast import FeatureStore
    
    store = FeatureStore(repo_path=".")

    Пример определений feature

    Следующий пример определяет одну entity, один файловый batch source, two feature views, one push source и one feature service. Вместе эти объекты достаточно, чтобы продемонстрировать регистрацию, online serving, materialization и push-обновления в одном repository.

    driver_stats_source читает batch-данные из data/driver_stats.parquet. driver_hourly_stats предоставляет эти поля для обычной materialization batch-to-online. driver_stats_push_source и driver_hourly_stats_fresh показывают, как та же entity может также получать свежие значения через push. driver_activity_v1 группирует feature view в повторно используемое serving-определение.

    Пример файла с определениями feature:

    from datetime import timedelta
    
    from feast import Entity, FeatureService, FeatureView, Field, FileSource, PushSource
    from feast.data_format import ParquetFormat
    from feast.types import Float32, Int64
    from feast.value_type import ValueType
    
    driver = Entity(name="driver", join_keys=["driver_id"], value_type=ValueType.INT64)
    
    driver_stats_source = FileSource(
        name="driver_stats_source",
        path="data/driver_stats.parquet",
        file_format=ParquetFormat(),
        timestamp_field="event_timestamp",
        created_timestamp_column="created",
    )
    
    driver_hourly_stats = FeatureView(
        name="driver_hourly_stats",
        entities=[driver],
        ttl=timedelta(days=365),
        schema=[
            Field(name="conv_rate", dtype=Float32),
            Field(name="acc_rate", dtype=Float32),
            Field(name="avg_daily_trips", dtype=Int64),
        ],
        online=True,
        source=driver_stats_source,
    )
    
    driver_stats_push_source = PushSource(
        name="driver_stats_push_source",
        batch_source=driver_stats_source,
    )
    
    driver_hourly_stats_fresh = FeatureView(
        name="driver_hourly_stats_fresh",
        entities=[driver],
        ttl=timedelta(days=365),
        schema=[
            Field(name="conv_rate", dtype=Float32),
            Field(name="acc_rate", dtype=Float32),
            Field(name="avg_daily_trips", dtype=Int64),
        ],
        online=True,
        source=driver_stats_push_source,
    )
    
    driver_activity_v1 = FeatureService(
        name="driver_activity_v1",
        features=[driver_hourly_stats],
    )

    CLI

    Запускайте feast apply из корневого каталога feature repository. В примере выше команда выполняется в <feature-repo>, а не в подкаталоге data/.

    feast apply читает feature_store.yaml из корня repository и рекурсивно сканирует Python-файлы в этом repository. Если определения feature хранятся в подкаталогах, команду все равно следует запускать из корня repository, если только эти файлы находятся внутри repository и не исключены через .feastignore.

    Если команда запускается из другого рабочего каталога, явно укажите repository:

    feast --chdir /path/to/<feature-repo> apply

    Форма по умолчанию:

    feast apply

    Настройка авторизации

    Авторизация на основе Kubernetes в Feast состоит из трех частей:

    1. Объявите имена ролей в CR FeatureStore.
    2. Определите объекты Feast Permission в feature repository, используя те же имена ролей.
    3. Свяжите пользователей Kubernetes или ServiceAccounts с этими ролями с помощью RoleBinding.

    Одного лишь объявления feast-reader и feast-writer в CR FeatureStore и привязки subjects к этим ролям недостаточно. Решения Feast по авторизации также требуют соответствующих определений Permission в feature repository.

    Пример фрагмента FeatureStore:

    spec:
      authz:
        kubernetes:
          roles:
            - feast-reader
            - feast-writer

    Пример определений Permission в feature repository:

    from feast import Entity, FeatureService, FeatureView
    from feast.permissions.action import ALL_ACTIONS, READ
    from feast.permissions.permission import Permission
    from feast.permissions.policy import RoleBasedPolicy
    
    reader_perm = Permission(
        name="reader_perm",
        types=[Entity, FeatureView, FeatureService],
        policy=RoleBasedPolicy(roles=["feast-reader"]),
        actions=READ,
    )
    
    writer_perm = Permission(
        name="writer_perm",
        types=[Entity, FeatureView, FeatureService],
        policy=RoleBasedPolicy(roles=["feast-writer"]),
        actions=ALL_ACTIONS,
    )

    После добавления или обновления объектов Permission выполните feast apply, чтобы метаданные авторизации были зарегистрированы в Feast.

    Пример конфигурации RoleBinding:

    apiVersion: v1
    kind: ServiceAccount
    metadata:
      name: feast-reader-sa
      namespace: <namespace>
    ---
    apiVersion: v1
    kind: ServiceAccount
    metadata:
      name: feast-writer-sa
      namespace: <namespace>
    ---
    apiVersion: rbac.authorization.k8s.io/v1
    kind: RoleBinding
    metadata:
      name: feast-reader-binding
      namespace: <namespace>
    subjects:
      - kind: ServiceAccount
        name: feast-reader-sa
        namespace: <namespace>
    roleRef:
      apiGroup: rbac.authorization.k8s.io
      kind: Role
      name: feast-reader
    ---
    apiVersion: rbac.authorization.k8s.io/v1
    kind: RoleBinding
    metadata:
      name: feast-writer-binding
      namespace: <namespace>
    subjects:
      - kind: ServiceAccount
        name: feast-writer-sa
        namespace: <namespace>
    roleRef:
      apiGroup: rbac.authorization.k8s.io
      kind: Role
      name: feast-writer

    Создайте пример токенов ServiceAccount:

    READER_TOKEN=$(kubectl create token feast-reader-sa -n <namespace>)
    WRITER_TOKEN=$(kubectl create token feast-writer-sa -n <namespace>)

    Если требуется пользовательское время жизни токена, добавьте --duration к команде.

    Конфигурация токена для SDK

    Когда включен authz.kubernetes, Feast Python client автоматически отправляет токен как bearer token. Для клиентов, работающих в том же кластере с подключенным токеном ServiceAccount, обычно не требуется дополнительная настройка SDK.

    Для внешних клиентов укажите токен одним из следующих способов:

    • задайте authz_config.user_token в feature_store.yaml
    • задайте переменную окружения LOCAL_K8S_TOKEN

    Пример фрагмента feature_store.yaml:

    authz_config:
      type: kubernetes
      user_token: <kubernetes-token>

    Пример переменной окружения:

    export LOCAL_K8S_TOKEN=<kubernetes-token>

    Дополнительные материалы

    Для end-to-end рабочих процессов Feast и более широкого использования продукта продолжите изучение официальной документации Feast:

    • Concepts: основные объекты Feast и модель данных
    • Architecture: модель развертывания, пути retrieval и шаблоны serving
    • Quickstart: end-to-end локальный workflow с использованием SDK
    • Sample use-case tutorials: обучающие материалы по сценариям для типовых ML workflows
    • Running Feast in production: production-паттерны и рекомендации по эксплуатации