Skip to main content

Installing on Kubernetes



Liteset ships a first-party Helm chart in this repository at helm/superset/. The chart was forked from the upstream Apache Superset chart and adjusted for the Liteset runtime — Uvicorn/uvloop launcher, pydantic-settings-based configuration, and the native WebSocket server (no superset-websocket sidecar).

Production reference

The Helm chart is the K8s companion to the Docker images documented in Production Docker Deployment. Read that page first for the required secrets, image targets (lean / dev / ci) and healthcheck endpoints.

Prerequisites

  • A Kubernetes cluster (1.27+ recommended)
  • Helm 3.10+
  • A clone of the liteset repository — the chart is consumed locally, it is not published to a Helm registry
note

For single-host environments we recommend minikube or kind, both of which work well with this chart.

Running

  1. Clone the repository
git clone --depth=1 https://github.com/happykust/liteset.git
cd liteset
  1. Inspect the bundled subcharts

The Liteset Helm chart depends on the Bitnami postgresql and redis subcharts (declared in helm/superset/Chart.yaml). They are vendored under helm/superset/charts/. Run helm dependency build helm/superset if your local cache is missing them.

Bitnami legacy images

Recent Bitnami releases moved most container images to a paid "Bitnami Premium" registry, so a fresh helm install may pull dockerhub.io/bitnamilegacy/postgresql:... and fail to start. The chart's default values.yaml pins working tags; if you override the PostgreSQL or Redis image, validate the tag exists publicly. See the troubleshooting notes in Production Docker Deployment for the same issue at the Docker layer.

  1. Configure your overrides

Create a my-values.yaml and override at least the items below. Every key is documented in helm/superset/values.yaml.

# my-values.yaml

# REQUIRED: secret key used to sign session cookies and encrypt secrets.
# Generate with: openssl rand -base64 42
extraSecretEnv:
LITESET_SECRET_KEY: "CHANGE_ME_TO_A_LONG_RANDOM_STRING"

# Optional: override the image. Defaults to the lean Liteset image.
# image:
# repository: ghcr.io/happykust/liteset
# tag: "6.0.0"
# pullPolicy: IfNotPresent

# Default values.yaml already exports SUPERSET_CONFIG_PATH so the
# rendered superset_config.py is picked up by pydantic-settings.
# Only override extraEnv if you need to inject additional variables.
extraEnv:
# Example: enable proxy fix behind an ingress that does TLS offloading.
# ENABLE_PROXY_FIX: "True"

LITESET_SECRET_KEY is mandatory — Liteset's SupersetSettings will refuse to start without it. SUPERSET_CONFIG_PATH is already set in the default values.yaml (it points at /app/pythonpath/superset_config.py) and almost never needs to be changed.

  1. Install
helm install superset helm/superset \
--values my-values.yaml \
--create-namespace --namespace superset

After a minute or so you should see something like:

kubectl -n superset get pods
NAME READY STATUS RESTARTS AGE
superset-celerybeat-7cdcc9575f-k6xmc 1/1 Running 0 119s
superset-f5c9c667-dw9lp 1/1 Running 0 4m7s
superset-f5c9c667-fk8bk 1/1 Running 0 4m11s
superset-init-db-zlm9z 0/1 Completed 0 111s
superset-postgresql-0 1/1 Running 0 6d20h
superset-redis-master-0 1/1 Running 0 6d20h
superset-worker-75b48bbcc-jmmjr 1/1 Running 0 4m8s
superset-worker-75b48bbcc-qrq49 1/1 Running 0 4m12s

The exact list depends on your overrides; you should generally expect:

  • N superset-xxxx-yyyy (web) and superset-worker-xxxx-yyyy (Celery worker) pods depending on supersetNode.replicaCount and supersetWorker.replicaCount
  • 1 superset-postgresql-0 (or your external PostgreSQL)
  • 1 superset-redis-master-0 (or your external Redis)
  • 1 superset-celerybeat-xxxx-yyyy if supersetCeleryBeat.enabled: true

There is no WebSocket sidecar — Liteset serves WebSockets natively from the main superset-xxxx-yyyy pods.

  1. Access it

The chart publishes Services to expose the Liteset UI within your cluster. To access it externally:

  • Configure the Service as a LoadBalancer or NodePort
  • Set up an Ingress (the chart includes a template; you'll want to tune hostname, TLS and annotations)
  • Run kubectl -n superset port-forward svc/superset 8088:8088 to tunnel locally

Then log in with the default admin / admin credentials (override with init.adminUser in your values).

Important settings

Security settings

Default passwords are baked into the chart for first-boot convenience but must be rotated for any non-disposable environment:

postgresql:
postgresqlPassword: "<strong random string>"

extraSecretEnv:
LITESET_SECRET_KEY: "<strong random string, openssl rand -base64 42>"

Liteset reads LITESET_SECRET_KEY from the environment. If you previously deployed with a different key and need to rotate it without losing encrypted database credentials, set the old value as PREVIOUS_SECRET_KEY in configOverrides and run superset re-encrypt-secrets from the init pod — the same procedure as upstream Apache Superset.

External PostgreSQL / Redis

To disable the bundled subcharts and point at managed services:

postgresql:
enabled: false

redis:
enabled: false

supersetNode:
connections:
db_host: "postgres.internal"
db_port: "5432"
db_user: "liteset"
db_pass: "..." # use envFromSecrets in production
db_name: "liteset"
redis_host: "redis.internal"
redis_port: "6379"

Dependencies

Extra Python packages can be installed via bootstrapScript (sourced by every pod at startup). For production clusters we strongly recommend baking these into a custom image instead — pods start faster and don't depend on PyPI being reachable at boot:

FROM ghcr.io/happykust/liteset:6.0.0
USER root
RUN . /app/.venv/bin/activate && uv pip install \
snowflake-sqlalchemy \
redshift-connector
USER superset

See Production Docker Deployment for the full custom-image workflow.

superset_config.py

The default superset_config.py rendered by the chart is intentionally minimal; you'll extend it via configOverrides:

configOverrides:
my_override: |
# Make sure the redirect_uri is properly computed when an ingress does TLS offloading
ENABLE_PROXY_FIX = True
FEATURE_FLAGS = {
"DYNAMIC_PLUGINS": True,
}

Each entry is rendered as a Helm template, so you can reference other values.yaml variables (e.g. {{ .Values.ingress.hosts[0] }}).

The entire superset_config.py is stored as a Secret in the cluster, so it is safe to put sensitive parameters directly inside configOverrides — though extraSecretEnv plus os.environ.get("VAR") is usually cleaner.

A full Python file can be loaded with:

helm upgrade --install --values my-values.yaml \
--set-file configOverrides.oauth=set_oauth.py \
superset helm/superset

Environment variables

extraEnv (plain ConfigMap) and extraSecretEnv (Secret) are both passed into the web, worker, beat and init pods. They can be referenced from superset_config.py via os.environ.get("VAR"):

extraEnv:
SMTP_HOST: smtp.gmail.com
SMTP_USER: user@gmail.com
SMTP_PORT: "587"
SMTP_MAIL_FROM: user@gmail.com

extraSecretEnv:
SMTP_PASSWORD: xxxx

configOverrides:
smtp: |
SMTP_HOST = os.getenv("SMTP_HOST", "localhost")
SMTP_STARTTLS = os.getenv("SMTP_STARTTLS", "True").lower() == "true"
SMTP_SSL = os.getenv("SMTP_SSL", "False").lower() == "true"
SMTP_USER = os.getenv("SMTP_USER", "superset")
SMTP_PORT = int(os.getenv("SMTP_PORT", "25"))
SMTP_PASSWORD = os.getenv("SMTP_PASSWORD", "superset")

System packages

If new system packages are required, install them by overriding the container command. The same pattern works for the web, worker and beat pods:

supersetWorker:
command:
- /bin/sh
- -c
- |
apt update
apt install -y somepackage
apt autoremove -yqq --purge
apt clean

# Run celery worker
. {{ .Values.configMountPath }}/superset_bootstrap.sh
celery --app=superset.tasks.celery_app:app worker

Data sources

Database connections can be declared declaratively via extraConfigs:

extraConfigs:
import_datasources.yaml: |
databases:
- allow_file_upload: true
allow_ctas: true
allow_cvas: true
database_name: example-db
extra: "{\r\n \"metadata_params\": {},\r\n \"engine_params\": {},\r\n \"\
metadata_cache_timeout\": {},\r\n \"schemas_allowed_for_file_upload\": []\r\n\
}"
sqlalchemy_uri: example://example-db.local
tables: []

These are mounted as Secrets and may include sensitive parameters.

Configuration examples

OAuth and SSO

OAuth, LDAP and other authentication backends are configured the same way as upstream Apache Superset — by overriding AUTH_TYPE, OAUTH_PROVIDERS and friends in superset_config.py. See the OAuth section of Configuring Liteset for the full configuration surface; copy the snippet into a configOverrides entry and put any client IDs/secrets in extraSecretEnv.

Enable Alerts and Reports

Follow the platform-agnostic Alerts and Reports documentation. On Kubernetes you will typically:

  1. Install a Playwright/Chromium-capable image for the Celery worker (either bake it into your custom image or install via bootstrapScript).
  2. Enable the Celery beat:
supersetCeleryBeat:
enabled: true
  1. Configure SMTP/Slack via extraEnv + extraSecretEnv (see the SMTP example above).

Load the example dashboards

init:
loadExamples: true

The superset-init-db Job will populate the metadata DB with example datasets and dashboards on first install.