Releases¶
This page tracks notable changes in Apache Superset Kubernetes Operator releases.
Unreleased¶
Added¶
- Helm
dnsPolicyanddnsConfig. The Helm chart now exposesdnsPolicyanddnsConfigvalues for the operator manager pod (#394, @younsl). - Helm
priorityClassName. The Helm chart now exposes apriorityClassNamevalue that sets the PriorityClass of the operator manager pods. Unset by default, which keeps the cluster default priority (#420, @younsl). - Removing default probes. Setting
livenessProbe,readinessProbe, orstartupProbeto{}now removes the operator's default probe. It works on every component and follows the usual top-level and per-component override rules (#427, @younsl). - Helm
extraEnv. The Helm chart now exposes anextraEnvvalue that appends environment variables to the operator manager container, for example aGOMEMLIMITderived from the memory limit.WATCH_NAMESPACEis rejected because thewatchblock owns it (#426, @younsl). supshort name. TheSupersetresource now has the short namesup, sokubectl get supworks the same askubectl get superset(#480, @younsl).
Changed¶
- Optional string values in the Helm chart (
image.tag,serviceAccount.name,logLevel,metrics.certSecretName,metrics.serviceMonitor.scrapeTimeout,dnsPolicy,podDisruptionBudget.unhealthyPodEvictionPolicy) now default to~(null) instead of"", matching the chart's other unset values. Rendered output is unchanged, and explicit empty strings are still accepted (#394, @younsl). - Breaking:
podTemplate.container.portsis removed. Each component now always listens on its operator default port, and its ServicetargetPort, default probes, and NetworkPolicy always target that port. Overriding the first port used to move the Service, probes, and NetworkPolicy without changing the port the server listened on, so the pods restarted in a loop. A port set on the top-levelpodTemplate.containerwas also merged into every HTTP component. Removeportsfrom your Superset resources before upgrading: the API server drops the field from stored resources, andkubectl applywith strict field validation rejects it. Instances that setportsgo back to the default port and roll once on upgrade. To change the port clients connect to, useservice.port(#462, @younsl). - Celery worker liveness probe. The Celery worker now gets a default liveness probe that runs
celery inspect pingagainst the pod's own worker node, so a worker that stays Running but no longer answers over the broker is restarted. Timings match the upstream Superset Helm chart (120s initial delay, 60s period and timeout, 3 failures). Existing worker Deployments roll once on upgrade, and settinglivenessProbeon the worker replaces the default (#427, @younsl).
0.3.1 - 2026-10-21¶
Fixed¶
- Credential redaction in lifecycle task failure messages now masks the whole value when a quoted credential key is followed by empty quotes and more characters, such as
{"password": ""hunter2}. Previously the characters after the empty quotes were left in the parent Superset status and Kubernetes Events (#437, @younsl). - Setting
spec.valkey.sslwithout certificate files (for examplessl: {}for managed Valkey or Redis with in-transit encryption) no longer crash-loops the Celery worker. The operator now rendersssl_cert_reqsand the Celerybroker_use_sslandredis_backend_use_ssloptions whenever SSL is enabled, andssl.certRequiredtakes effect without certificate paths. Deployments that use SSL roll once on upgrade (#440, @younsl). - Built with Go 1.27.2 and
golang.org/x/netv0.60.0, which pick up upstream security fixes.
0.3.0 - 2026-09-30¶
Added¶
- Structured metastore, Valkey, and lifecycle seed-source connection fields can now be sourced individually from Kubernetes Secret keys, allowing
Supersetresources to consume provisioner-owned endpoints and credentials without copying discovered values or assembling a separate connection URI (#369). - Helm
podDisruptionBudget. The Helm chart now exposes apodDisruptionBudgetvalue that renders a PodDisruptionBudget for the operator manager pods. It is disabled by default and falls back tomaxUnavailable: 1when no bound is set. Rendering fails for integer or percentage bounds that would leave zero allowed disruptions at the configuredreplicas(for exampleminAvailable: 1with one replica, ormaxUnavailable: 0), so the budget never blocks node drains. See High availability for the recommended multi-replica setup.unhealthyPodEvictionPolicycan be set toAlwaysAllowso drains can evict a crash-looping manager (#386, @younsl).
Changed¶
- Helm chart requires leader election for multiple replicas. Rendering now fails when
replicasis greater than 1 andleaderElection.enabledisfalse. Replicas are active/standby behind the leader election Lease; without it every replica reconciles the sameSupersetresources and races on Jobs, drains, and status. Existing releases with that combination failhelm upgradeuntil leader election is enabled or the release is scaled to one replica (#390, @younsl). - Valkey's default port is now applied at runtime, aligning it with the existing structured-metastore behavior, instead of being stored by CRD defaulting. Resources that omit both
valkey.portandvalkey.portFromtherefore no longer materializeport: 6379, while generated configuration continues to use port 6379. This permitsportFromwithout a defaulted literal conflicting at admission (#369). - Kubernetes support now covers the three newest
kind-published minor versions instead of two. CI tests Kubernetes 1.37, 1.36, and 1.35 natively, with the experimentalnextlane disabled again (#315).
Fixed¶
- The default MySQL tool image for the seed task and the
createDatabaseinit container is nowmysql:8.4. The previous default,mysql:8-alpine, does not exist on Docker Hub, so MySQL seeding and database auto-creation failed with an image pull error unless an image was set explicitly. Staging instances that seed from MySQL with the default image re-seed once after upgrading, because the seed image is part of the seed task checksum (#389, @younsl). - The operator-managed maintenance page now sets
seccompProfile: RuntimeDefaulton its container, so it is admitted in namespaces enforcing the restricted Pod Security Standard (its other hardened defaults were already set, but the missing seccomp profile caused rejection) (#362, @villebro). - The operator no longer crash-loops on clusters where Gateway API is installed but serves only
v1beta1: optional-API detection now pins the version the operator actually uses (HTTPRoutev1,ServiceMonitorv1) instead of matching any version of the Kind (#361, @villebro). - Component Services of type
NodePortorLoadBalancerthat do not pinservice.nodePortno longer churn: the operator now preserves the apiserver-allocated node port across reconciles instead of triggering a re-allocation each time, which previously changed the external port and broke external access (#360, @villebro). - The operator now requests
updateonsupersets/finalizers, so reconciliation no longer fails on clusters with theOwnerReferencesPermissionEnforcementadmission plugin enabled (e.g. OpenShift), where the API server previously rejected theblockOwnerDeletionowner references the operator sets on child resources (#359, @villebro). - The chart no longer rejects top-level values it does not declare, so shared values files and deploy tooling that injects release metadata no longer fail schema validation. Nested value blocks are still strictly validated (#366, @ThomasJLLN).
Security¶
- Every operator-created container (component Deployments, lifecycle task Jobs, and the create-database init container) now defaults to a hardened securityContext —
allowPrivilegeEscalation: false, all capabilities dropped, andseccompProfile: RuntimeDefault— filled per-field only where you have not set them yourself. This hardens workloads on permissive clusters and satisfies several of the restricted Pod Security Standard's requirements out of the box; full restricted compatibility still requires user-provided non-root settings (runAsNonRoot/runAsUserare not defaulted, because the Superset image declares a named user and a numeric UID cannot be safely defaulted across vanilla and OpenShift clusters). This changes pod templates, so workloads roll once on upgrade (#363, @villebro). - Breaking: CRs with
serviceAccount.create=true(or unset) andserviceAccount.name != metadata.nameare now rejected at admission. To use a pre-existing ServiceAccount with a different name, setserviceAccount.create=false(#324, @villebro). - Instances that had pinned the
superset.apache.org/config-checksumpod annotation roll once on upgrade as the operator's computed checksum reasserts itself, closing a gap where a pinned annotation could freeze out config andSECRET_KEYrotations while status misreported as reconciled (#331, @villebro). - Breaking: Valkey cache and results-backend
keyPrefixvalues are now constrained to^[A-Za-z0-9._:-]*$(max 128 characters); values containing spaces, slashes, or other characters outside that set are rejected. The safer rendering also causes a one-time config-checksum change and pod roll on upgrade (#325, @villebro). - Seed
excludeTables,excludeTableData, andpostSeedSQLvalues are now passed literally to generated seed scripts; values that previously relied on shell expansion no longer expand (#325, @villebro). - Breaking: Celery Flower is no longer published on the Ingress/Gateway surface in
Productionby default. Flower's default command ships without authentication and its dashboard discloses task names and arguments — for Superset, other users' async SQL Lab statements and alert/report payloads. InProduction(the default) Flower is fanned out onto the end-user host — and its port opened in the built-in NetworkPolicy — only when you explicitly setceleryFlower.service.gatewayPath;DevelopmentandStagingcontinue to publish it by default. To keep exposing Flower in Production, setceleryFlower.service.gatewayPath(e.g./flower) after placing authentication in front of it (e.g.FLOWER_BASIC_AUTHinjected from a Secret viaceleryFlower.podTemplate.container.env) (#279, @villebro). - Breaking: A
ProductionSuperset CR can no longer be changed in place toDevelopmentorStaging; delete and recreate the instance to change environment out ofProduction. Upgrades towardProductionand non-Production transitions are unaffected (#327, @villebro).
0.2.0 - 2026-08-11¶
Added¶
- Seconds and year precision in
cronSchedule. Lifecycle taskcronSchedulefields now accept 6- and 7-field cron expressions in addition to the classic 5-field form — an optional leading seconds field and/or trailing year field (e.g.*/30 * * * * *every 30 seconds,0 0 2 * * * 2027). Existing 5-field schedules are unaffected (#238, @villebro). - Helm
imagePullSecrets. The Helm chart now exposes animagePullSecretsvalue that setsspec.template.spec.imagePullSecretson the operator Deployment, letting operators pull the manager image from a private registry. The referenced Secrets must already exist in the release namespace — the chart does not create them (#240, @younsl). - Helm
topologySpreadConstraints. The Helm chart now exposes atopologySpreadConstraintsvalue that setsspec.template.spec.topologySpreadConstraintson the operator Deployment, letting operators distribute manager pods across failure domains such as nodes and zones (#213, @younsl). - Helm
revisionHistoryLimit. The Helm chart now exposes arevisionHistoryLimitvalue that allows settingspec.revisionHistoryLimiton the operator Deployment, capping the number of old ReplicaSets retained for rollback (@younsl). - Helm extra manifests. The Helm chart now supports
extraManifestsfor rendering trusted, release-scoped Kubernetes manifests with Helmtpl. Use it for companion resources owned by the operator release, not shared cluster infrastructure such as Gateway API controllers, CRDs, or shared Gateways (#196, @younsl). - Helm resize policy. The Helm chart now supports
resizePolicyon the manager container, controlling whether an in-place pod resize (InPlacePodVerticalScaling) restarts the container (#200, @younsl).
Changed¶
- Breaking: renamed the "version" status fields to "tag".
status.version→status.tag(thekubectl getcolumn is renamed Version → Tag), andstatus.lifecycle.upgrade.fromVersion/toVersion→fromTag/toTag. No behavior change. - Breaking: downgrade blocking is removed. Any change to the lifecycle image tag now re-runs the migrate task (
superset db upgrade) regardless of direction — the operator no longer performs semver comparison or setsstatus.phase: Blockedon a version decrease. The migrate task only runssuperset db upgrade(Superset's down migrations are poorly tested and often break, so the operator never runs them), so take a database backup before an upgrade if you may need to revert. Thedirectionfield is removed fromstatus.lifecycle.upgrade, and theVersionComparisonSkippedwarning event no longer fires. - Breaking: the lifecycle
clonetask is renamed toseed. Renamespec.lifecycle.clonetospec.lifecycle.seed(and itspostCloneSQLfield topostSeedSQL) in your Superset resources. The task Job name suffix changes from-cloneto-seed, and the lifecycle status phase fromCloningtoSeeding. Customseed.commandscripts must read the renamedSUPERSET_OPERATOR__SEED_SRC_*environment variables.
Security¶
- Credential redaction in task failure output. Lifecycle task failure messages are now scrubbed with best-effort pattern-based redaction before being persisted to the parent Superset status and Kubernetes Events: passwords embedded in connection URIs and common credential assignments (
password=...,token=..., etc.) are masked. This mitigates the known limitation where a failing task command could leak credential fragments into status (@younsl).
0.1.1 - 2026-06-29¶
Fixed¶
- Honor HPA-managed replica counts: the operator no longer overwrites the replica count on Deployments whose scaling is owned by a HorizontalPodAutoscaler (#152, @pashtet04).
0.1.0 - 2026-06-10¶
Added¶
- Initial release (@villebro).
Known limitations¶
- Websocket server is experimental. The websocket server is not yet well supported and is pending security hardening; it is not recommended for production use.
- Downgrade protection requires semver image tags. Downgrades are detected and blocked only when both image tags are valid semver. Non-semver tags (
latest, date stamps, digest pins) cannot be ordered, so the operator emits aVersionComparisonSkippedwarning and proceeds without blocking. See Lifecycle. - Task failure messages may include credential fragments. Lifecycle task failure output is truncated into
statusand could contain fragments of task stdout, including credentials. See security.md.