keda: multitenant setup#423
Merged
Merged
Conversation
4990cd5 to
22bb202
Compare
eff3384 to
e349f69
Compare
There was a problem hiding this comment.
Pull request overview
Adds initial Helm chart support for a Kedify-flavored multi-tenant KEDA deployment by introducing new multitenancy values and wiring them into rendered manifests (metrics-server config, tenant registration, and scoped RBAC), while also preventing webhook ClusterRole(/Binding) creation when webhooks are disabled.
Changes:
- Introduce
kedify.multitenant.*values to model"default"vs"tenant"deployment modes. - Add tenant registration + agent secret-reader RBAC manifests, and default-tenant multitenancy Secret/Role wiring for the metrics API server.
- Gate webhook ClusterRole/ClusterRoleBinding creation on
webhooks.enabled(in addition torbac.create).
Reviewed changes
Copilot reviewed 9 out of 9 changed files in this pull request and generated 4 comments.
Show a summary per file
| File | Description |
|---|---|
| keda/values.yaml | Adds kedify.multitenant configuration surface and inline docs. |
| keda/templates/webhooks/clusterrolebindings.yaml | Only renders webhook ClusterRoleBinding when webhooks are enabled. |
| keda/templates/webhooks/clusterrole.yaml | Only renders webhook ClusterRole when webhooks are enabled. |
| keda/templates/metrics-server/kedify-role.yaml | Adds namespaced Role/RoleBinding used in multitenant default mode. |
| keda/templates/metrics-server/kedify-multitenancy-config.yaml | Adds the (initially empty) Secret used for multitenancy configuration in default mode. |
| keda/templates/metrics-server/deployment.yaml | Wires multitenancy env var + Secret/emptyDir mounts into the metrics API server pod. |
| keda/templates/manager/deployment.yaml | Adds tenant-mode env var and tweaks arg formatting. |
| keda/templates/kedify-tenant-registration-configmap.yaml | Adds tenant registration ConfigMap emitted when multitenancy mode is enabled. |
| keda/templates/kedify-agent-secret-rbac.yaml | Adds Role/RoleBinding granting the kedify-agent read access to the tenant TLS Secret. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Signed-off-by: Zbynek Roubalik <zroubalik@gmail.com>
Signed-off-by: Jan Wozniak <wozniak.jan@gmail.com>
Signed-off-by: Jan Wozniak <wozniak.jan@gmail.com>
Signed-off-by: Jan Wozniak <wozniak.jan@gmail.com>
Signed-off-by: Jan Wozniak <wozniak.jan@gmail.com>
Two fixes so multiple keda operators can coexist (multitenant tenant mode), including in the same namespace as the default install: - webhook ServiceAccount was created regardless of webhooks.enabled, so a tenant install (webhooks.enabled=false) collided with the default release's keda-webhook SA. Gate it on webhooks.enabled like every other webhook object. - tenant operators sharing a namespace contended for the same leader-election lock (operator.keda.sh) and only one became leader. Default the lock to the (unique) operator.name in tenant mode. Both per-namespace and single-namespace multi-operator topologies now install and run with the chart's normal RBAC, no manual cluster-admin.
- tenant registration ConfigMap derives the operator gRPC address from .Values.clusterDomain instead of a hardcoded cluster.local, so non-default cluster domains register the correct address. - fix the multitenant mode description (grammar + correct *-metrics-apiserver naming) and note that tenant installs need a unique operator.name to avoid cluster RBAC collisions. - drop trailing whitespace on the cert-rotation arg.
The hand-maintained values.schema.json had no entry for the kedify.* values, so kedify.multitenant.* was unvalidated. Add a Kedify definition (mode enum ""/default/tenant, configSecretName, address, authority, agentNamespace, agentServiceAccount) so Helm validates these on lint/template/install and IDEs can autocomplete them.
The multitenant provider (kedify/keda#88) now emits Events via the new events.k8s.io API instead of the deprecated core/v1 record.EventRecorder. Point the metrics-server's dedicated kedify Role at the events.k8s.io group so connection-state events aren't rejected as forbidden. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
- apply standard keda.labels (+ additionalAnnotations) to the tenant registration ConfigMap and the multitenancy-config Secret, matching the rest of the chart so label/annotation-based policies select them - fix the values.yaml gRPC address doc to reference <clusterDomain> (the template default) instead of hardcoded cluster.local Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
wozniakjan
commented
Jun 10, 2026
ConfigMap data values must be strings; an all-numeric namespace would render as a YAML int and be rejected. Quote it like the other data fields. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
A tenant install only runs its own keda-operator; the metrics apiserver, admission webhooks and CRDs are cluster singletons owned by the single mode=default install. Gate those templates (and the operator's webhook / apiservice caBundle patching) on mode!=tenant so a tenant never deploys a second adapter, re-installs CRDs, or patches the default's webhook/APIService. Tenants no longer need to set metricsServer.enabled=false / webhooks.enabled=false / crds.install=false: mode=tenant + a unique operator.name is enough. Cert generation, the operator and its RBAC still render for tenants. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
kedifybot
approved these changes
Jun 12, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
KEDA chart modifications for multitenant KEDA setup.
By default, KEDA is deployed in single-tenant mode. By setting
kedify.multitenant.modetodefault, KEDA deploys the full KEDA stack while staying aware of tenant deployments that may join later. There can be only a single KEDA withkedify.multitenant.mode: default. Additional tenants are deployed withkedify.multitenant.mode: tenant.Each install (the default and every tenant) creates a
kedify.io/tenant-registrationConfigMap describing its operator address and TLS secret. Thekedify-agentdiscovers these across namespaces and populates thekedify-multitenancy-configSecret in the default install's namespace, which the shared metrics adapter reads to route each namespace's HPA requests to the right tenant operator.Requires kedify-agent with multitenant feature enabled
Default KEDA multitenant deployment (must be exactly one default KEDA):
Secondary tenant KEDA deployments (an arbitrary number of tenants can be installed). In
tenantmode the shared singletons (metrics apiserver, admission webhooks, CRDs) are disabled automatically, so a tenant just needs a uniqueoperator.name:When several tenants share a single namespace, also override
serviceAccount.operator.nameandcertificates.secretNameso they stay unique.see also: #424