Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
54 changes: 24 additions & 30 deletions infra/charts/feast/README.md
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
# Feast Java Helm Charts (alpha)
# Feast Helm Charts

This repo contains Helm charts for Feast Java components that are being installed on Kubernetes:
This repo contains Helm charts for Feast components that are being installed on Kubernetes:
* Feast (root chart): The complete Helm chart containing all Feast components and dependencies. Most users will use this chart, but can selectively enable/disable subcharts using the values.yaml file.
* [Feature Server](charts/feature-server): High performant JVM-based implementation of feature server.
* [Feature Server](charts/feature-server): Python-based online feature serving service.
* [Transformation Service](charts/transformation-service): Transformation server for calculating on-demand features
* Redis: (Optional) One of possible options for an online store used by Feature Server

Expand All @@ -21,45 +21,39 @@ helm repo add feast-charts https://feast-helm-charts.storage.googleapis.com
helm repo update
```

Install Feast
Install Feast (using an existing Secret — recommended for production):
```
helm install feast-release feast-charts/feast
kubectl create secret generic my-feast-config \
--from-literal=feature_store_yaml_base64=$(base64 < feature_store.yaml)

helm install feast-release feast-charts/feast \
--set feature-server.existingSecret=my-feast-config
```

Or pass the config inline (the value will be stored in Helm release metadata):
```
helm install feast-release feast-charts/feast \
--set feature-server.feature_store_yaml_base64=$(base64 < feature_store.yaml)
```

## Customize your installation

This Feast chart comes with a [values.yaml](values.yaml) that allows for configuration and customization of all sub-charts.

In order to modify the default configuration of Feature Server, please use the `application-override.yaml` key in the `values.yaml` file in this chart. A code snippet example
```
feature-server:
application-override.yaml:
enabled: true
feast:
active_store: online
stores:
- name: online
type: REDIS
config:
host: localhost
port: 6379
entityKeySerializationVersion: 3

global:
registry:
path: gs://[YOUR GCS BUCKET]/demo-repo/registry.db
cache_ttl_seconds: 60
project: feast_java_demo
The feature server requires a base64-encoded `feature_store.yaml`. You can either reference a pre-existing Kubernetes Secret or provide the value inline:

```yaml
feature-server:
# Option A: reference an existing Secret (recommended)
existingSecret: my-feast-config
# Option B: provide inline (stored in Helm release metadata)
feature_store_yaml_base64: <base64 encoded feature_store.yaml>
```

For the default configuration, please see the [Feature Server Configuration](https://github.com/feast-dev/feast/blob/master/java/serving/src/main/resources/application.yml).
> **Upgrading from the Java chart?** See the [feature-server migration guide](charts/feature-server/README.md#migration-from-java-chart) for details on removed gRPC and Java-specific values.

For more details, please see: https://docs.feast.dev/how-to-guides/running-feast-in-production

## Example
See [here](https://github.com/feast-dev/feast/tree/master/examples/java-demo) for a sample tutorial on testing this helm chart with a demo feature repository and a local Redis instance.

## Requirements

| Repository | Name | Version |
Expand All @@ -79,4 +73,4 @@ See [here](https://github.com/feast-dev/feast/tree/master/examples/java-demo) fo
| global.registry.path | string | `"gs://path/to/registry.db"` | Path to the registry file managed by Feast Python SDK |
| redis.enabled | bool | `false` | Flag to install Redis |
| redis.usePassword | bool | `false` | Disable redis password |
| transformation-service.enabled | bool | `true` | |
| transformation-service.enabled | bool | `true` | |
113 changes: 84 additions & 29 deletions infra/charts/feast/charts/feature-server/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,47 +6,103 @@ Feast Feature Server: Online feature serving service for Feast

**Homepage:** <https://github.com/feast-dev/feast>

## Migration from Java chart

This chart now deploys the Python-based feature server instead of the Java-based one.

### Removed values (no equivalent)

These Java-specific values have been removed. Delete them from your values files:

| Removed value | Reason |
|---|---|
| `javaOpts` | Python server, no JVM |
| `logType`, `logLevel` | Java logging config, not applicable |
| `transformationService.*` | Use the separate `transformation-service` subchart |
| `application.yaml`, `application-generated.yaml` | Java Spring config, not applicable |
| `application-override.yaml` | Replaced by `feature_store_yaml_base64` or `existingSecret` |
| `application-secret.yaml` | Replaced by `feature_store_yaml_base64` or `existingSecret` |

### Changed values

| Old value | New value | Notes |
|---|---|---|
| `service.grpc.port` | `service.port` | Protocol changed from gRPC to HTTP |
| `service.grpc.targetPort` | (removed) | `targetPort` now uses the named port `http` |
| `service.grpc.nodePort` | `service.nodePort` | Flat key |
| `ingress.grpc.*` | (removed) | Python server is HTTP-only |
| `ingress.http.class` | (removed) | Use `ingress.http.ingressClassName` or `annotations` |
| `ingress.http.auth.*` | (removed) | Use `ingress.http.annotations` for controller-specific auth |
| `ingress.http.whitelist` | (removed) | Use `ingress.http.annotations` for controller-specific whitelist |
| `image.repository` | `image.repository` | Changed from `feature-server-java` to `feature-server` |

### New values

| Value | Purpose |
|---|---|
| `feature_store_yaml_base64` | Base64-encoded `feature_store.yaml`, stored in a K8s Secret |
| `existingSecret` | Reference a pre-created Secret instead of providing inline config |
| `ingress.http.ingressClassName` | Support for `networking.k8s.io/v1` IngressClass |

### What still works

- `ingress.http.*` — same value structure, now uses `networking.k8s.io/v1`
- `secrets` — volume mounts for additional Kubernetes secrets
- `envOverrides` — extra environment variables
- `service.type`, `service.loadBalancerIP`, `service.loadBalancerSourceRanges`
- All probe settings (`livenessProbe.*`, `readinessProbe.*`)

## Installation

### Option A: Using an existing Secret (recommended)

Create the Secret outside of Helm so that credentials never pass through Helm values or release metadata:

```bash
kubectl create secret generic my-feast-config \
--from-literal=feature_store_yaml_base64=$(base64 < feature_store.yaml)
```

Then reference it during install:
```bash
helm install feast-feature-server . --set existingSecret=my-feast-config
```

This is the recommended approach when `feature_store.yaml` contains registry or online-store credentials.

### Option B: Using inline config

```bash
helm install feast-feature-server . --set feature_store_yaml_base64=$(base64 < feature_store.yaml)
```

> **Note:** When using `--set`, the base64-encoded config is stored in Helm release metadata and is retrievable via `helm get values`. Use Option A or an external secrets operator (e.g. SealedSecrets, ExternalSecrets) for production deployments with sensitive credentials.

## Values

| Key | Type | Default | Description |
|-----|------|---------|-------------|
| "application-generated.yaml".enabled | bool | `true` | Flag to include Helm generated configuration. Please set `application-override.yaml` to override this configuration. |
| "application-override.yaml" | object | `{"enabled":true}` | Configuration to override the default [application.yaml](https://github.com/feast-dev/feast/blob/master/java/serving/src/main/resources/application.yml). Will be created as a ConfigMap. `application-override.yaml` has a higher precedence than `application-secret.yaml` |
| "application-secret.yaml" | object | `{"enabled":false}` | Configuration to override the default [application.yaml](https://github.com/feast-dev/feast/blob/master/java/serving/src/main/resources/application.yml). Will be created as a Secret. `application-override.yaml` has a higher precedence than `application-secret.yaml`. It is recommended to either set `application-override.yaml` or `application-secret.yaml` only to simplify config management. |
| "application.yaml".enabled | bool | `true` | Flag to include the default [configuration](https://github.com/feast-dev/feast/blob/master/java/serving/src/main/resources/application.yml). Please set `application-override.yaml` to override this configuration. |
| envOverrides | object | `{}` | Extra environment variables to set |
| existingSecret | string | `""` | Name of an existing Secret containing key `feature_store_yaml_base64` with base64-encoded config |
| feature_store_yaml_base64 | string | `""` | [required] a base64 encoded version of feature_store.yaml (stored in a K8s Secret) |
| image.pullPolicy | string | `"IfNotPresent"` | Image pull policy |
| image.repository | string | `"quay.io/feastdev/feature-server-java"` | Docker image for Feature Server repository |
| image.repository | string | `"quay.io/feastdev/feature-server"` | Docker image for Feature Server repository |
| image.tag | string | `"0.65.0"` | Image tag |
| ingress.grpc.annotations | object | `{}` | Extra annotations for the ingress |
| ingress.grpc.auth.enabled | bool | `false` | Flag to enable auth |
| ingress.grpc.class | string | `"nginx"` | Which ingress controller to use |
| ingress.grpc.enabled | bool | `false` | Flag to create an ingress resource for the service |
| ingress.grpc.hosts | list | `[]` | List of hostnames to match when routing requests |
| ingress.grpc.https.enabled | bool | `true` | Flag to enable HTTPS |
| ingress.grpc.https.secretNames | object | `{}` | Map of hostname to TLS secret name |
| ingress.grpc.whitelist | string | `""` | Allowed client IP source ranges |
| ingress.http.annotations | object | `{}` | Extra annotations for the ingress |
| ingress.http.auth.authUrl | string | `"http://auth-server.auth-ns.svc.cluster.local/auth"` | URL to an existing authentication service |
| ingress.http.auth.enabled | bool | `false` | Flag to enable auth |
| ingress.http.class | string | `"nginx"` | Which ingress controller to use |
| ingress.http.annotations | object | `{}` | Extra annotations for the ingress (use for controller-specific settings) |
| ingress.http.enabled | bool | `false` | Flag to create an ingress resource for the service |
| ingress.http.hosts | list | `[]` | List of hostnames to match when routing requests |
| ingress.http.https.enabled | bool | `true` | Flag to enable HTTPS |
| ingress.http.https.secretNames | object | `{}` | Map of hostname to TLS secret name |
| ingress.http.whitelist | string | `""` | Allowed client IP source ranges |
| javaOpts | string | `nil` | [JVM options](https://docs.oracle.com/cd/E22289_01/html/821-1274/configuring-the-default-jvm-and-java-arguments.html). For better performance, it is advised to set the min and max heap: <br> `-Xms2048m -Xmx2048m` |
| ingress.http.ingressClassName | string | `nil` | IngressClass resource name |
| livenessProbe.enabled | bool | `true` | Flag to enabled the probe |
| livenessProbe.failureThreshold | int | `5` | Min consecutive failures for the probe to be considered failed |
| livenessProbe.initialDelaySeconds | int | `60` | Delay before the probe is initiated |
| livenessProbe.periodSeconds | int | `10` | How often to perform the probe |
| livenessProbe.successThreshold | int | `1` | Min consecutive success for the probe to be considered successful |
| livenessProbe.timeoutSeconds | int | `5` | When the probe times out |
| logLevel | string | `"WARN"` | Default log level, use either one of `DEBUG`, `INFO`, `WARN` or `ERROR` |
| logType | string | `"Console"` | Log format, either `JSON` or `Console` |
| nodeSelector | object | `{}` | Node labels for pod assignment |
| podAnnotations | object | `{}` | Annotations to be added to Feast Serving pods |
| podLabels | object | `{}` | Labels to be added to Feast Serving pods |
| podAnnotations | object | `{}` | Annotations to be added to Feature Server pods |
| podLabels | object | `{}` | Labels to be added to Feature Server pods |
| readinessProbe.enabled | bool | `true` | Flag to enabled the probe |
| readinessProbe.failureThreshold | int | `5` | Min consecutive failures for the probe to be considered failed |
| readinessProbe.initialDelaySeconds | int | `15` | Delay before the probe is initiated |
Expand All @@ -55,13 +111,12 @@ Feast Feature Server: Online feature serving service for Feast
| readinessProbe.timeoutSeconds | int | `10` | When the probe times out |
| replicaCount | int | `1` | Number of pods that will be created |
| resources | object | `{}` | CPU/memory [resource requests/limit](https://kubernetes.io/docs/concepts/configuration/manage-compute-resources-container/#resource-requests-and-limits-of-pod-and-container) |
| secrets | list | `[]` | List of Kubernetes secrets to be mounted. These secrets will be mounted on /etc/secrets/<secret name>. |
| service.grpc.nodePort | string | `nil` | Port number that each cluster node will listen to |
| service.grpc.port | int | `6566` | Service port for GRPC requests |
| service.grpc.targetPort | int | `6566` | Container port serving GRPC requests |
| secrets | list | `[]` | List of Kubernetes secrets to be mounted on /etc/secrets/\<secret name\> |
| service.loadBalancerIP | string | `nil` | Specify a load balancer IP if service type is LoadBalancer |
| service.loadBalancerSourceRanges | list | `[]` | Optionally restrict load balancer traffic to specified IPs |
| service.nodePort | string | `nil` | Port number that each cluster node will listen to |
| service.port | int | `6566` | Service port |
| service.type | string | `"ClusterIP"` | Kubernetes service type |
| transformationService.host | string | `""` | |
| transformationService.port | int | `6566` | |

----------------------------------------------
Autogenerated from chart metadata using [helm-docs v1.14.2](https://github.com/norwoodj/helm-docs/releases/v1.14.2)
23 changes: 23 additions & 0 deletions infra/charts/feast/charts/feature-server/templates/NOTES.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
Feast Feature Server has been deployed.

{{- if and (not .Values.existingSecret) (not .Values.feature_store_yaml_base64) }}

WARNING: Neither "existingSecret" nor "feature_store_yaml_base64" is set.
The feature server will fail to start without a valid feature_store.yaml.

Option A (recommended): create a Secret and reference it:
kubectl create secret generic my-feast-config \
--from-literal=feature_store_yaml_base64=$(base64 < feature_store.yaml)
helm upgrade {{ .Release.Name }} . --set existingSecret=my-feast-config

Option B: provide inline:
helm upgrade {{ .Release.Name }} . \
--set feature_store_yaml_base64=$(base64 < feature_store.yaml)
{{- end }}

{{- if and .Values.feature_store_yaml_base64 (not .Values.existingSecret) }}

NOTE: "feature_store_yaml_base64" is stored in Helm release metadata.
If feature_store.yaml contains credentials, consider using "existingSecret"
to keep sensitive data out of Helm values.
{{- end }}
24 changes: 12 additions & 12 deletions infra/charts/feast/charts/feature-server/templates/_helpers.tpl
Original file line number Diff line number Diff line change
Expand Up @@ -25,21 +25,21 @@ If release name contains chart name it will be used as a full name.
{{- end -}}

{{/*
Create chart name and version as used by the chart label.
Common labels
*/}}
{{- define "feature-server.chart" -}}
{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" -}}
{{- define "feature-server.labels" -}}
app: {{ include "feature-server.name" . }}
component: serving
chart: {{ .Chart.Name }}-{{ .Chart.Version | replace "+" "_" }}
release: {{ .Release.Name }}
heritage: {{ .Release.Service }}
{{- end -}}

{{/*
Common labels
Selector labels
*/}}
{{- define "feature-server.labels" -}}
app.kubernetes.io/name: {{ include "feature-server.name" . }}
helm.sh/chart: {{ include "feature-server.chart" . }}
app.kubernetes.io/instance: {{ .Release.Name }}
{{- if .Chart.AppVersion }}
app.kubernetes.io/version: {{ .Chart.AppVersion | quote }}
{{- end }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
{{- define "feature-server.selectorLabels" -}}
app: {{ include "feature-server.name" . }}
component: serving
release: {{ .Release.Name }}
{{- end -}}

This file was deleted.

Loading
Loading