Kubernetes kan automatisk justere antall podder basert på CPU-bruk, men hva skjer når lastbelastningen handler om antall meldinger i en kø, ikke prosessorsyklusar? Det er her KEDA kommer inn. KEDA, kort for Kubernetes Event-driven Autoscaling, er et CNCF-prosjekt som ble gradert til høyeste modenhetsnivå i foundationen 22. august 2023, samme nivå som Kubernetes og Prometheus selv. Prosjektet startet som et samarbeid mellom Microsoft og Red Hat, og ligger i dag på rundt 10 600 stjerner på GitHub. I denne guiden setter vi opp KEDA fra bunnen av, kobler den til en kø-basert arbeidsmengde, og viser hvordan du unngår de vanligste fellene når podder skal skalere helt ned til null og tilbake opp igjen.

Målgruppen er plattformteam i Norden som allerede kjører Kubernetes i produksjon, enten på EKS, AKS, GKE eller en selvstyrt klynge, og som er lei av å betale for podder som står og venter på jobb som aldri kommer. Vi bruker rundt 60 minutter på hele oppsettet, fra installasjon til feilsøking av en skalering som ikke trigges.

For nordiske plattformteam handler dette ofte om mer enn ren teknisk eleganse. Når strøm- og driftskostnader i skyen presses opp samtidig som FinOps-rapportering blir en fast del av budsjettprosessen, er evnen til å la podder gå helt til null et konkret sparetiltak, ikke bare en smart funksjon. En kø-konsument som kjører 24 timer i døgnet men kun behandler meldinger i 3 timer, betaler for 21 timer med inaktiv beregningskraft hver eneste dag. Multipliser det med et titalls mikrotjenester i en klynge, og besparelsen fra riktig konfigurert KEDA blir fort synlig på fakturaen fra skyleverandøren.

Hva er KEDA, og hvorfor er det forskjellig fra HPA

Kubernetes sin innebygde Horizontal Pod Autoscaler (HPA) leser CPU- og minnebruk, eller egendefinerte metrikker via en metrics-adapter, og justerer antall replikaer deretter. Det fungerer godt for jevn, forutsigbar trafikk. Problemet oppstår når arbeidsmengden din ikke er knyttet til CPU i det hele tatt, for eksempel en kø-konsument som ligger i ro det meste av døgnet og plutselig må behandle 50 000 meldinger på ti minutter.

KEDA løser ikke dette ved å erstatte HPA. Ifølge AWS sin egen dokumentasjon for EKS fungerer KEDA ved å spørre en ekstern kilde, som Prometheus eller en meldingskø, og deretter opprette og styre en vanlig Kubernetes HPA-ressurs i bakgrunnen. Det gjør at du beholder alt det kjente HPA-rammeverket, men får et mye bredere sett med datakilder å skalere på. Microsofts Open Source-blogg beskrev prosjektet ved lanseringen slik: “KEDA provides a FaaS-like model of event-aware scaling, where deployments can dynamically scale to and from zero based on demand.” Det er nettopp skalering til og fra null som er KEDAs mest brukte funksjon i praksis, siden standard HPA ikke er bygget for å ta en arbeidsmengde ned til null replikaer og vekke den igjen når en hendelse inntreffer.

Forskjellen mellom KEDA, HPA og Vertical Pod Autoscaler (VPA) kan oppsummeres kort: HPA svarer på “hvor mange podder trenger vi basert på en metrikk”, VPA svarer på “hvor mye CPU og minne bør hver podd be om”, og KEDA svarer på “hvor mange podder trenger vi basert på ventende, eksternt arbeid, inkludert om svaret er null”. De tre kan kombineres, men du bør aldri la VPA og HPA style samme ressurs (CPU) samtidig, da det fører til at de to kontrollerne motarbeider hverandre.

EgenskapKEDAHPAVPA
HovedfunksjonEndrer antall podder, inkludert skalering til/fra nullEndrer antall podderJusterer CPU/minne per podd
Typiske datakilderKøer, strømmer, meldingsmeglere, Prometheus, skytjenester, cronCPU, minne, egendefinerte metrikkerHistorisk og nåværende ressursbruk
Skalering til nullJa, for støttede hendelseskilderNeiIkke relevant (styrer ikke replikaer)
Krever metrics-adapterNei, har egne “scalers”Ofte, for egendefinerte metrikkerNei
Forhold til HPAOppretter og styrer en HPA-ressursEr selve den native ressursenUavhengig kontroller

Forutsetninger før du starter

Før du installerer KEDA bør du ha følgende på plass. Dette er ikke bare en sjekkliste, versjonskrav har faktisk endret seg mellom KEDA-utgivelser, og å hoppe over dem er den vanligste årsaken til at installasjonen feiler på trinn fire.

  • En kjørende Kubernetes-klynge, enten lokal (kind, minikube) eller administrert (EKS, AKS, GKE). KEDA 2.x krever Kubernetes 1.24 eller nyere i de fleste nyere utgivelser, men sjekk alltid de spesifikke versjonsnotatene for utgaven du installerer, siden minstekravet justeres opp over tid.
  • kubectl, konfigurert mot riktig kontekst.
  • Helm versjon 3, siden Helm-metoden er den mest brukte og best dokumenterte installasjonsveien.
  • Cluster-admin-rettigheter eller tilsvarende, fordi KEDA installerer egne CRD-er (Custom Resource Definitions) og en metrics-adapter som krever klyngenivå-tilganger.
  • En arbeidsmengde å teste med. Vi bruker en enkel kø-konsument i eksemplene, men prinsippet er det samme uansett om du skalerer på Kafka, RabbitMQ, Azure Service Bus eller Prometheus-metrikker.
  • Minst 15-30 minutter uforstyrret tid, siden skalering til null tar noen minutter å observere i praksis.

Et viktig poeng om versjonsnummer: offisielle utgivelsessider for kedacore/keda har historisk vist sprikende informasjon avhengig av når siden ble hentet inn på nytt, og den nyeste stabile utgivelsen endrer seg oftere enn denne artikkelen oppdateres. Derfor bygger vi inn en verifiseringskommando i selve installasjonen (trinn 3) i stedet for å hardkode et versjonsnummer du uansett bør dobbeltsjekke selv.

Test lokalt med kind eller minikube før produksjon

Før du rører en produksjonsklynge, bør du gjøre hele øvelsen én gang på en lokal klynge. Det koster deg ti minutter, men sparer deg for ubehagelige overraskelser senere, spesielt rundt admission-webhooker og CRD-versjoner som kan oppføre seg litt annerledes på eldre klynger.

kind create cluster --name keda-test
kubectl cluster-info --context kind-keda-test

# Installer RabbitMQ lokalt for testing
helm repo add bitnami https://charts.bitnami.com/bitnami
helm install rabbitmq bitnami/rabbitmq --namespace meldingskoe --create-namespace

Kjør gjennom hele installasjonsprosessen fra trinn 1 til trinn 9 nedenfor på denne testklyngen, med redusert maxReplicaCount og en lavere terskelverdi, slik at du ser hele skaleringsforløpet i løpet av et par minutter i stedet for å vente på reell produksjonstrafikk. Når alt fungerer som forventet lokalt, er du klar til å gjenta nøyaktig samme manifester mot EKS, AKS eller GKE, kun med riktige produksjonsverdier for secrets og ressursgrenser.

Steg 1: Verifiser klyngen og noter utgangspunktet

Start alltid med å dokumentere tilstanden før du endrer noe. Dette gjør feilsøking enklere hvis noe går galt, og gir deg et konkret “før”-bilde å sammenligne med etterpå.

kubectl version --short
kubectl get nodes -o wide
kubectl get namespaces
kubectl top nodes 2>/dev/null || echo "Metrics Server er ikke installert ennå"

Hvis siste kommando feiler, må du installere Metrics Server separat først, siden både HPA og KEDAs CPU-baserte scalers er avhengige av den. KEDA i seg selv krever ikke Metrics Server for kø- og strømbaserte scalers, men du vil ofte trenge den for generell klyngeovervåking uansett.

Steg 2: Opprett navnerom og legg til Helm-repoet

KEDA installeres vanligvis i et eget navnerom, isolert fra applikasjonene som skal skaleres. Det gjør opprydding og rettighetsstyring enklere senere.

kubectl create namespace keda

helm repo add kedacore https://kedacore.github.io/charts
helm repo update

Legg merke til at Helm-repoet heter kedacore, og chart-navnet er keda. Det er lett å forveksle disse med kommandoer du finner i eldre blogginnlegg som peker til en annen repo-URL, siden KEDA har flyttet distribusjonskanal en gang tidligere i prosjektets historie.

Steg 3: Finn og pin en konkret chart-versjon

Dette er trinnet de fleste hopper over, og det er nettopp derfor produksjonsinstallasjoner av KEDA ofte bryter sammen uanmeldt ved neste “helm upgrade”. List alle tilgjengelige versjoner, og velg en bestemt versjon bevisst i stedet for å stole på “latest”.

helm search repo kedacore/keda --versions | head -10

Output vil se omtrent slik ut (versjonsnumrene hos deg vil være nyere enn dette eksempelet, siden prosjektet gir ut oppdateringer jevnlig):

NAME                CHART VERSION   APP VERSION   DESCRIPTION
kedacore/keda       2.17.2          2.17.2        KEDA helm chart for app scaling...
kedacore/keda       2.17.1          2.17.1        KEDA helm chart for app scaling...
kedacore/keda       2.16.1          2.16.1        KEDA helm chart for app scaling...

Installer deretter med eksplisitt versjonsflagg, slik at du vet nøyaktig hva som kjører, og kan reprodusere installasjonen på et annet miljø.

helm install keda kedacore/keda \
  --namespace keda \
  --version 2.17.2 \
  --set watchNamespace="" \
  --wait

Flagget watchNamespace satt til tom streng betyr at KEDA overvåker alle navnerom i klyngen. I et delt klyngemiljø med flere team bør du i stedet begrense dette til navnerommene som faktisk trenger autoskalering, både av sikkerhetshensyn og for å redusere unødvendig belastning på KEDAs operator-komponent.

Steg 4: Bekreft at komponentene kjører

En vellykket installasjon gir deg flere kjørende komponenter, blant annet operator og metrics-apiserver. Sjekk begge før du går videre.

kubectl get pods -n keda
kubectl get crd | grep keda

Du bør se CRD-er som ScaledObject, ScaledJob og TriggerAuthentication. Mangler en av disse, er installasjonen ikke komplett, og du bør kjøre “helm status keda -n keda” for å se om Helm rapporterer feil fra admission-webhooken.

Steg 5: Velg riktig scaler for arbeidsmengden din

KEDAs katalog av “scalers” er det som gjør prosjektet nyttig. En scaler er en adapter mellom en ekstern hendelseskilde og KEDAs skaleringslogikk. De mest brukte i nordiske produksjonsmiljøer er Prometheus (for egendefinerte applikasjonsmetrikker), AWS SQS og CloudWatch, Azure Service Bus og Storage Queues, Apache Kafka, RabbitMQ, PostgreSQL/MySQL (for kø-tabeller), Redis og Redis Streams, Google Cloud Pub/Sub, samt en enkel cron-scaler for tidsstyrt skalering, for eksempel ned til null utenom arbeidstid.

KEDAs egen dokumentasjon beskriver prosjektets kjernefunksjon slik: “KEDA is a tool that helps Kubernetes scale applications based on real-world events.” Det er et greit mentalt bilde å ta med seg videre: du definerer hva et “real-world event” betyr for akkurat din arbeidsmengde, og KEDA oversetter det til et konkret replika-tall.

For resten av denne guiden bruker vi RabbitMQ som eksempel, siden det er en av de mest brukte meglerne i nordiske mikrotjeneste-arkitekturer, og mønsteret er direkte overførbart til SQS, Kafka eller Service Bus.

Et vanlig spørsmål er om man kan kombinere flere scalers på samme arbeidsmengde, for eksempel både Prometheus og RabbitMQ i samme ScaledObject. Svaret er ja, og KEDA håndterer dette ved å evaluere alle triggerne parallelt og skalere etter den som til enhver tid krever flest replikaer. Dette er nyttig for arbeidsmengder som både prosesserer en kø og eksponerer et HTTP-endepunkt, der du vil skalere på kølengde i rolige perioder men også reagere raskt på responstid hvis trafikken plutselig kommer fra et annet sted enn køen.

Steg 6: Definer en ScaledObject for en kø-konsument

En ScaledObject er den sentrale ressursen i KEDA. Den peker til en eksisterende Deployment, definerer min/maks antall replikaer, og beskriver én eller flere triggere (scalers) som bestemmer når skalering skal skje.

apiVersion: keda.sh/v1alpha1
kind: ScaledObject
metadata:
  name: ordre-konsument-scaler
  namespace: produksjon
spec:
  scaleTargetRef:
    name: ordre-konsument
  minReplicaCount: 0
  maxReplicaCount: 30
  cooldownPeriod: 120
  pollingInterval: 15
  triggers:
    - type: rabbitmq
      metadata:
        queueName: ordre-ko
        mode: QueueLength
        value: "20"
      authenticationRef:
        name: rabbitmq-auth

Her sier vi at hver podd bør håndtere rundt 20 meldinger i køen, at vi tillater fra 0 til 30 replikaer, at KEDA sjekker køen hvert 15. sekund (pollingInterval), og at systemet venter 120 sekunder med lav kølengde (cooldownPeriod) før det skalerer helt ned til null igjen. Denne cooldown-perioden er avgjørende: sett den for lavt, og du får “flapping”, der podder konstant startes og stoppes idet kølengden svinger rundt terskelverdien.

Steg 7: Håndter autentisering med TriggerAuthentication

Legg aldri tilkoblingsstrenger eller API-nøkler direkte i en ScaledObject. KEDA har en egen ressurstype, TriggerAuthentication, som peker til en Kubernetes Secret eller en ekstern hemmelighetstjeneste.

apiVersion: v1
kind: Secret
metadata:
  name: rabbitmq-secret
  namespace: produksjon
type: Opaque
stringData:
  host: "amqp://bruker:[email protected]:5672"
---
apiVersion: keda.sh/v1alpha1
kind: TriggerAuthentication
metadata:
  name: rabbitmq-auth
  namespace: produksjon
spec:
  secretTargetRef:
    - parameter: host
      name: rabbitmq-secret
      key: host

Hvis du kjører på Azure, bør du være oppmerksom på at KEDA fra og med versjon 2.15 fjernet støtte for Pod Identity som autentiseringsmetode. Microsofts egen AKS-dokumentasjon anbefaler nå Workload Identity i stedet, så sjekk at TriggerAuthentication-ressursen din peker til riktig mekanisme hvis du oppgraderer en eksisterende klynge og ikke gjør en fersk installasjon.

Steg 8: Installer eksempelapplikasjonen og generer last

For å se KEDA i aksjon trenger du noe som faktisk legger meldinger i køen. Et enkelt skript holder i testfasen.

kubectl apply -f deployment-ordre-konsument.yaml
kubectl apply -f scaledobject.yaml

# Generer testlast mot RabbitMQ (kjor fra en port-forward eller en jobb i klyngen)
for i in $(seq 1 500); do
  curl -s -u bruker:passord -X POST \
    http://localhost:15672/api/exchanges/%2f/amq.default/publish \
    -H "Content-Type: application/json" \
    -d '{"properties":{},"routing_key":"ordre-ko","payload":"test-melding","payload_encoding":"string"}'
done

Følg deretter med på podder og HPA i to separate terminalvinduer.

kubectl get pods -n produksjon -w
kubectl get hpa -n produksjon -w

Steg 9: Tolk output og bekreft skalering

Innen 15-30 sekunder etter at køen passerer terskelen, bør du se en HPA-ressurs med navnet “keda-hpa-ordre-konsument-scaler” dukke opp automatisk. Dette bekrefter at KEDA gjør akkurat det dokumentasjonen beskriver: den oppretter og styrer en vanlig HPA bak kulissene, du trenger aldri å lage denne selv.

$ kubectl get hpa -n produksjon
NAME                               REFERENCE                    TARGETS   MINPODS   MAXPODS   REPLICAS
keda-hpa-ordre-konsument-scaler    Deployment/ordre-konsument   45/20     0         30        3

Når køen tømmes og cooldown-perioden på 120 sekunder har passert, bør REPLICAS gå tilbake til 0. Hvis podden blir hengende på 1 i stedet for å gå til 0, er det som regel enten feil minReplicaCount i ScaledObject, eller en PodDisruptionBudget som blokkerer siste podd fra å avsluttes.

Du kan også følge forløpet via klyngens hendelseslogg, som gir et mer detaljert bilde av hvorfor en bestemt skalering skjedde akkurat da den gjorde:

$ kubectl get events -n produksjon --field-selector involvedObject.kind=HorizontalPodAutoscaler
LAST SEEN   TYPE     REASON              OBJECT                                        MESSAGE
45s         Normal   SuccessfulRescale   hpa/keda-hpa-ordre-konsument-scaler          New size: 6; reason: external metric rabbitmq above target
12s         Normal   SuccessfulRescale   hpa/keda-hpa-ordre-konsument-scaler          New size: 11; reason: external metric rabbitmq above target

Denne loggen er ofte raskere å feilsøke med enn å stirre på et “kubectl get pods”-vindu, siden den forteller deg eksplisitt hvilken metrikk som trigget rescale-hendelsen og hva det nye måltallet var. Hvis du aldri ser noen SuccessfulRescale-hendelser til tross for at køen fylles opp, er det et sterkt signal om at selve triggeren, ikke selve podd-skaleringen, er der problemet ligger.

Steg 10: Legg til en ScaledJob for batch-arbeid (valgfritt)

For engangsoppgaver, som rapportgenerering eller bildeprosessering, passer ofte en ScaledJob bedre enn en ScaledObject. I stedet for å skalere en Deployment, oppretter KEDA en ny Kubernetes Job per hendelse, noe som er mer robust for oppgaver som må kjøre helt til ferdig uten å bli avbrutt av en vanlig scale-down.

apiVersion: keda.sh/v1alpha1
kind: ScaledJob
metadata:
  name: bildeprosessering-job
  namespace: produksjon
spec:
  jobTargetRef:
    template:
      spec:
        containers:
          - name: prosessor
            image: registry.intern/bildeprosessering:1.4.0
        restartPolicy: Never
  pollingInterval: 10
  maxReplicaCount: 50
  triggers:
    - type: aws-sqs-queue
      metadata:
        queueURL: https://sqs.eu-north-1.amazonaws.com/123456789/bilde-ko
        queueLength: "1"
        awsRegion: eu-north-1

Merk at AWS-regionen her er satt til eu-north-1, som er AWS sin Stockholm-region, det nærmeste AWS-alternativet for norske team som må holde data innenfor Norden av hensyn til ytelse eller interne krav til datalokasjon.

Steg 11: Overvåk KEDA med Prometheus-metrikker

KEDA eksponerer egne metrikker om operatorens helsetilstand og skaleringsbeslutninger, uavhengig av hvilken scaler du bruker for selve arbeidsmengden. Dette er avgjørende i produksjon, siden en feilkonfigurert scaler ofte feiler stille, uten at noen podder krasjer, de bare skalerer ikke.

kubectl port-forward -n keda svc/keda-operator-metrics-apiserver 9022:9022
curl -s http://localhost:9022/metrics | grep keda_scaler_errors

Legg disse metrikkene inn i Prometheus og sett opp et varsel når keda_scaler_errors øker over null over en periode på fem minutter. Det er typisk tegn på at autentiseringen mot den eksterne køen eller meglertjenesten har sluttet å fungere, for eksempel fordi en hemmelighet er rotert uten at TriggerAuthentication ble oppdatert.

Steg 12: Rull ut gradvis og sett grenser for ressursbruk

Siste steg handler om disiplin, ikke nye kommandoer. Sett alltid resources.requests og resources.limits på podder som styres av KEDA, siden rask oppskalering fra null til tretti replikaer kan presse klyngens nodekapasitet hardt på få sekunder hvis ingen grenser er satt. Kombiner gjerne med Cluster Autoscaler eller Karpenter på nodenivå, slik at klyngen kan legge til noder raskt nok til å følge KEDAs podnivå-skalering.

Test alltid i et ikke-produksjonsmiljø først med maxReplicaCount satt lavere enn produksjonsverdien, observer atferden over minst én full arbeidsdag, og øk gradvis. Mange team setter maxReplicaCount altfor høyt i første forsøk og opplever uventede regninger fra skyleverandøren når en uventet meldingsflom trigger full skalering.

Full fungerende prosjektstruktur

Her er hele oppsettet samlet, slik det bør se ut i et Git-repo for et reelt prosjekt.

keda-autoskalering/
|-- namespace.yaml
|-- helm/
|   `-- install-keda.sh
|-- manifests/
|   |-- secret.yaml
|   |-- trigger-authentication.yaml
|   |-- scaledobject.yaml
|   `-- scaledjob.yaml
`-- README.md

# install-keda.sh
#!/usr/bin/env bash
set -euo pipefail
helm repo add kedacore https://kedacore.github.io/charts
helm repo update
helm upgrade --install keda kedacore/keda \
  --namespace keda --create-namespace \
  --version 2.17.2 \
  --wait --timeout 5m
kubectl apply -f manifests/secret.yaml
kubectl apply -f manifests/trigger-authentication.yaml
kubectl apply -f manifests/scaledobject.yaml
echo "KEDA installert og ScaledObject anvendt."

Komplett eksempel: en norsk netthandel skalerer ordrebehandling

Sett sammen blir et realistisk produksjonsoppsett slik: et norsk netthandelsselskap kjører en ordre-konsument på EKS i eu-north-1, som normalt mottar få bestillinger om natten men opplever kraftige topper rundt lunsj og i forbindelse med kampanjer. Teamet installerer KEDA via Helm med versjon pinnet eksplisitt, oppretter navnerommet produksjon, og legger ScaledObject-en fra trinn 6 med minReplicaCount satt til 0 og maxReplicaCount satt til 30.

I en vanlig natt står ordre-konsumenten på 0 replikaer fra midnatt til klokken seks, siden køen er tom og cooldownPeriod på 120 sekunder har rukket å utløpe. Når morgentrafikken starter rundt klokken syv, begynner meldinger å hope seg opp i RabbitMQ, og innen 30 sekunder ser teamet den automatisk opprettede HPA-ressursen “keda-hpa-ordre-konsument-scaler” dukke opp med stigende REPLICAS-tall. Under en kampanjedag med 20 ganger normal trafikk skalerer arbeidsmengden helt opp til taket på 30 podder i løpet av to-tre minutter, og Cluster Autoscaler på nodenivå legger automatisk til flere noder for å gi plass til de nye poddene.

Etter kampanjen avtar trafikken gradvis, og podder skaleres ned trinnvis etter hvert som kølengden synker under terskelverdien på 20 meldinger per podd. Innen cooldown-perioden har utløpt for siste gang, er arbeidsmengden tilbake på 0 replikaer, og selskapet betaler ingenting for beregningskraft i de lange periodene uten bestillinger. Teamet følger med på keda_scaler_errors i Prometheus gjennom hele forløpet, og mottar ingen varsler, et tegn på at autentiseringen mot RabbitMQ har fungert stabilt gjennom både den stille natten og kampanjetoppen.

Vanlige fallgruver ved KEDA-oppsett

  • Feil pollingInterval. Satt for lavt, genererer det unødvendig last mot den eksterne køen eller API-et. Satt for høyt, reagerer skaleringen for sent på plutselige topper. 15-30 sekunder er et fornuftig startpunkt for de fleste kø-baserte scalers.
  • cooldownPeriod satt for lavt. Fører til “flapping”, der podder starter og stopper om hverandre i rask takt, noe som sliter på både applikasjonen og klyngens kontrollplan.
  • Glemt TriggerAuthentication. Uten denne feiler scaleren stille, HPA-ressursen opprettes, men viser alltid 0/20 selv når køen er full.
  • minReplicaCount satt til 1 i stedet for 0. Da går du glipp av hele poenget med KEDA, nemlig å betale for null podder når det ikke er arbeid å gjøre.
  • Manglende ressursgrenser på podder. Rask skalering fra null til mange titalls replikaer uten requests/limits kan utløse nodepress og OOM-kill-hendelser.
  • Blande VPA og HPA på CPU-metrikken for samme Deployment. De to kontrollerne kjemper om det samme tallet og gir uforutsigbar atferd.
  • Feil navnerom i watchNamespace. Hvis KEDA kun overvåker ett navnerom, men ScaledObject ligger i et annet, skjer det rett og slett ingenting, uten noen tydelig feilmelding.
  • Hardkodet “latest” i stedet for pinnet versjon. En Helm-installasjon uten eksplisitt –version henter alltid nyeste chart ved neste “helm upgrade”, noe som kan introdusere brytende endringer midt i en vanlig driftsrutine uten at noen i teamet planla for det.
  • Glemmer å teste nedskalering, kun oppskalering. Mange team tester at podder starter riktig under last, men glemmer å verifisere at de faktisk går tilbake til minReplicaCount etterpå. Skaleringsfeil nedover er vanskeligere å oppdage fordi de ikke påvirker brukeropplevelsen direkte, bare regningen.

Skaler-sammenligning: hvilken passer din arbeidsmengde

ScalerTypisk bruksområdeKrever TriggerAuthenticationStøtter skalering til null
RabbitMQKø-konsumenter, mikrotjenesterJa, for tilkoblingsstrengJa
AWS SQSServerless-lignende batch og event-prosesseringJa, via IAM-rolle eller nøklerJa
Azure Service BusBedriftsintegrasjon, meldingskøer i .NET-miljøerJaJa
Apache KafkaStrømprosessering, event sourcingJa, for SASL/TLSJa, basert på consumer lag
PrometheusEgendefinerte applikasjonsmetrikkerValgfrittJa
CronTidsstyrt opp-/nedskalering, f.eks. utenom arbeidstidNeiJa
PostgreSQL/MySQLKø-tabeller, batch-jobber mot databaserJaJa

Feilsøking: de vanligste problemene og løsningene

  • HPA-ressursen opprettes aldri. Sjekk at ScaledObject faktisk peker til riktig Deployment-navn i scaleTargetRef, og at navnerommet stemmer. Kjør “kubectl describe scaledobject” for å se events-feltet, som ofte avslører årsaken direkte.
  • keda_scaler_errors øker i metrikkene. Dette er nesten alltid et autentiseringsproblem. Bekreft at Secret-ressursen inneholder riktige verdier, og at TriggerAuthentication peker til riktig Secret og nøkkelnavn.
  • Podder skalerer opp, men aldri ned til null. Sjekk PodDisruptionBudget-ressurser i navnerommet. En PDB med minAvailable satt til 1 vil aktivt hindre siste podd fra å avsluttes, uansett hva ScaledObject sier.
  • “Flapping” mellom 0 og 1 replika. Øk cooldownPeriod, og vurder å sette en lavere terskelverdi i triggeren slik at systemet ikke balanserer nøyaktig på kanten av terskelen.
  • Helm-installasjonen feiler med en “admission webhook”-feil. Dette skjer oftest ved oppgradering fra en eldre KEDA-versjon uten at gamle CRD-er er fjernet først. Fjern de spesifikke KEDA CRD-ene og installer på nytt, men kun i testmiljø, aldri direkte i produksjon uten en plan for nedetid.
  • Azure Pod Identity-autentisering slutter å virke etter oppgradering. Som nevnt tidligere fjernet KEDA 2.15 støtte for denne mekanismen. Du må migrere til Workload Identity, en endring Microsoft dokumenterer i sin AKS-dokumentasjon for KEDA.
  • Skaleringen er for treg ved brå lasttopper. Reduser pollingInterval, men vær oppmerksom på at dette øker antall kall mot den eksterne køen. For svært brå topper, vurder en lavere terskelverdi i stedet, slik at skalering trigges tidligere i forløpet.
  • Operator-podden i keda-navnerommet krasjer gjentatte ganger. Sjekk ressursgrenser på selve KEDA-operatoren. I klynger med svært mange ScaledObject-ressurser (over hundre) kan standard minnegrense bli for lav, og du må øke den via Helm-verdiene.

Avanserte tips for produksjonsmiljø

Når grunnoppsettet er stabilt, er det noen grep som skiller et hobby-oppsett fra noe som tåler produksjonslast. Bruk flere triggere i samme ScaledObject når en arbeidsmengde faktisk reagerer på mer enn én kilde, for eksempel både kølengde og en Prometheus-metrikk for responstid. KEDA evaluerer alle triggere og skalerer etter den som krever flest replikaer.

Vurder også “fallback”-konfigurasjon i ScaledObject, en innstilling som lar systemet falle tilbake til et fast replika-antall hvis scaleren mister kontakt med den eksterne kilden i en gitt periode. Dette hindrer at hele arbeidsmengden skalerer ned til null bare fordi en overvåkingskilde midlertidig er utilgjengelig, noe som ellers kan forårsake et unødvendig driftsavbrudd.

For team som kjører flere hundre ScaledObject-ressurser i samme klynge, bør du dele opp KEDA-installasjonen med egne watchNamespace-verdier per team eller miljø, i stedet for én sentral installasjon som overvåker alt. Det reduserer blåseradius hvis operatoren skulle få problemer, og gjør det enklere å gi hvert team egen kontroll over sine egne ScaledObject-ressurser uten å måtte involvere plattformteamet for hver endring.

Til slutt: kombiner alltid KEDA med nodenivå-autoskalering. Hvis Kubernetes-klyngen din ikke kan legge til noder raskt nok, hjelper det ikke at KEDA ber om 30 nye podder på sekundet, de vil bare stå i Pending-tilstand til nodekapasiteten følger med.

Et annet produksjonsgrep er å teste skaleringsatferden under last før du stoler på den i et reelt kampanjescenario. Bruk et enkelt lastgenereringsskript til å simulere en brå kø-oppbygging i et testmiljø som speiler produksjonskonfigurasjonen, og mål faktisk tid fra meldingene legges i køen til nye podder begynner å behandle dem. Dette tallet, ofte kalt “time to scale”, bør være en kjent og dokumentert verdi for teamet ditt, ikke noe dere finner ut for første gang midt i en reell trafikktopp. Noter også hvor lang tid det tar før klyngen skalerer ned igjen etter at lasten avtar, siden det direkte påvirker hvor mye dere faktisk sparer i beregningskostnad.

Vurder til slutt å sette opp strukturerte varsler, ikke bare på keda_scaler_errors, men også på antall podder som treffer maxReplicaCount over tid. Hvis en arbeidsmengde konsekvent ligger på taket i flere minutter i strekk, er det et tegn på at maxReplicaCount bør økes, eller at det underliggende systemet (meldingskøen, databasen, eller en nedstrøms-tjeneste) ikke følger med på den faktiske etterspørselen uansett hvor mange podder KEDA starter.

KEDA på tvers av skyleverandører

Støtten for KEDA varierer en del mellom de tre store skyleverandørene, og det er verdt å kjenne forskjellen før du velger installasjonsmetode. Azure har kommet lengst med førstepartsintegrasjon: AKS tilbyr en administrert KEDA-tilleggskomponent som kan aktiveres direkte via Azure CLI eller Azure-portalen, og den nyere varianten AKS Automatic kommer med KEDA forhåndskonfigurert. Hvilken KEDA-versjon som faktisk installeres, avhenger av hvilken Kubernetes-versjon AKS-klyngen kjører, så sjekk komponenttabellen i Microsofts dokumentasjon før du planlegger en oppgradering.

AWS dokumenterer KEDA som en integrasjon for EKS, blant annet for autoskalering av maskinlæringsarbeidsmengder basert på HPA og KEDA sammen, men har ikke en tilsvarende administrert tilleggskomponent, du installerer selv via Helm slik vi har vist i denne guiden. Google dokumenterer på samme måte en fremgangsmåte for å installere KEDA på GKE for skalering til null, typisk via Helm-chartet eller et YAML-manifest hentet direkte fra prosjektets GitHub-utgivelser. Uansett skyleverandør er selve ScaledObject- og TriggerAuthentication-ressursene identiske, det er kun installasjonsveien og hvilke scalers som er mest naturlig å bruke, som varierer.

SkyleverandørInstallasjonsmetodeAdministrert tilleggskomponentAnbefalt autentisering
Azure AKSAdministrert add-on via CLI/portal, eller HelmJa, inkludert i AKS AutomaticWorkload Identity
AWS EKSHelm-chart (selvinstallert)Nei, ingen egen AWS-administrert variantIAM-rolle via IRSA eller Pod Identity
Google GKEHelm-chart eller YAML-manifest fra GitHub-utgivelserNei, ingen egen Google-administrert variantWorkload Identity Federation
Selvstyrt klyngeHelm-chart eller OperatorHubIkke relevantKubernetes Secrets eller ekstern hemmelighetstjeneste

Legg merke til at kun Azure tilbyr en fullt administrert KEDA-variant i dag. På AWS og Google Cloud er du selv ansvarlig for å følge med på nye utgivelser og oppgradere i tråd med egen endringshåndtering, noe som gjør trinn 3 i denne guiden (pinning av chart-versjon) enda viktigere enn på AKS, der Microsoft til en viss grad styrer versjonen for deg basert på klyngens Kubernetes-versjon.

For team som drifter arbeidsmengder på tvers av flere skyer samtidig, for eksempel en hovedklynge på EKS og en sekundær på AKS av beredskapshensyn, er det verdt å merke seg at ScaledObject- og TriggerAuthentication-manifestene i praksis kan gjenbrukes uendret mellom skyene, så lenge selve scaler-typen (RabbitMQ, Kafka og lignende) ikke er bundet til én spesifikk sky. Kun selve autentiseringsmekanismen, altså hvordan TriggerAuthentication kobles til IAM-rolle eller Workload Identity, må tilpasses hver sky. Dette gjør KEDA til et av de mer portable autoskaleringsverktøyene tilgjengelig i dag, sammenlignet med skyspesifikke løsninger som er tettere bundet til én enkelt leverandørs infrastruktur.

Sikkerhet og tilgangsstyring rundt KEDA

KEDAs endringslogg har historisk inkludert retting av sårbarheter arvet fra Go sitt standardbibliotek, deriblant CVE-2024-24789, CVE-2024-24790 og CVE-2024-24791, som ble lukket i en tidligere utgivelsessyklus. Det understreker et generelt poeng: hold KEDA-versjonen oppdatert på linje med andre klyngekomponenter, siden sårbarheter i underliggende avhengigheter (som Go-biblioteket) kan påvirke operatoren selv om feilen ikke stammer fra KEDA-koden.

Gi aldri KEDA-operatoren bredere RBAC-tilganger enn nødvendig. Standard Helm-chart setter opp fornuftige roller, men hvis du tilpasser disse, pass på at operatoren kun får lese Secrets i navnerommene den faktisk trenger å overvåke. Bruk dedikerte service-kontoer per sky-integrasjon (IAM-rolle for AWS, Workload Identity for Azure/GCP) fremfor delte legitimasjoner på tvers av flere ScaledObject-ressurser, slik at en kompromittert nøkkel ikke gir tilgang til mer enn strengt nødvendig.

Revider også TriggerAuthentication-ressursene jevnlig, på samme måte som dere reviderer andre hemmeligheter i klyngen. Fordi disse ressursene ofte opprettes tidlig i et prosjekt og sjelden røres igjen, er det lett å glemme at de peker til legitimasjon som kan ha blitt rotert eller trukket tilbake andre steder i systemet. Et godt vanemønster er å inkludere TriggerAuthentication og tilhørende Secret i samme revisjonssjekk dere allerede gjør for andre klyngehemmeligheter, i stedet for å behandle KEDA-konfigurasjonen som et eget, isolert system utenfor den vanlige sikkerhetsrutinen.

Ofte stilte spørsmål om KEDA og autoskalering i Kubernetes

Er KEDA et erstatningsprodukt for Horizontal Pod Autoscaler?
Nei. KEDA utvider HPA ved å gi den flere datakilder å reagere på, og oppretter selv en vanlig HPA-ressurs i bakgrunnen. Du fjerner ikke HPA fra klyngen når du installerer KEDA, du gir den bare flere ting å lytte til.

Kan KEDA skalere podder helt ned til null?
Ja, for scalers som støtter det, inkludert kø-baserte triggere som RabbitMQ, SQS og Kafka. Dette er en av hovedgrunnene til at team velger KEDA fremfor ren HPA, siden standard HPA ikke er designet for å ta en arbeidsmengde til null replikaer.

Trenger jeg Prometheus for å bruke KEDA?
Nei. Prometheus er én av mange mulige scalers, ikke en forutsetning for prosjektet. Du kan kjøre KEDA utelukkende med kø- eller strømbaserte triggere uten noen Prometheus-installasjon i det hele tatt.

Hvilken Kubernetes-versjon trenger jeg for å kjøre KEDA?
Minstekravet endres mellom KEDA-utgivelser. Sjekk alltid versjonsnotatene for den spesifikke chart-versjonen du installerer (se trinn 3 i denne guiden), i stedet for å stole på et tall du har lest andre steder, siden kravet har økt over tid etter hvert som eldre Kubernetes-versjoner har gått ut av support.

Er KEDA et CNCF-prosjekt, og hva betyr det i praksis?
Ja. KEDA ble tatt opp i CNCF 12. mars 2020, flyttet til Incubating-nivå 18. august 2021, og ble gradert til Graduated-nivå 22. august 2023, samme modenhetsnivå som Kubernetes og Prometheus. Det betyr at prosjektet har gjennomgått foundationens strengeste krav til styresett, sikkerhetspraksis og vedlikehold.

Kan jeg bruke KEDA sammen med Karpenter eller Cluster Autoscaler?
Ja, og det anbefales i produksjon. KEDA styrer antall podder basert på hendelser, mens Karpenter eller Cluster Autoscaler sørger for at klyngen faktisk har nok noder til å kjøre dem. De to løser forskjellige lag av samme skaleringsproblem.

Hvorfor skalerer ikke ScaledObject selv om køen har meldinger?
De vanligste årsakene er manglende eller feil TriggerAuthentication, feil navn på Deployment i scaleTargetRef, eller at KEDA-operatoren ikke overvåker navnerommet fordi watchNamespace er feil konfigurert. Kjør “kubectl describe scaledobject” som første feilsøkingssteg.

Koster det noe ekstra å kjøre KEDA i en administrert klynge som AKS eller EKS?
Selve KEDA-komponenten er et gratis, åpen kildekode-prosjekt. På AKS er den administrerte tilleggskomponenten inkludert i AKS-prisen. På EKS og GKE installerer du den selv via Helm uten ekstra lisenskostnad, du betaler kun for beregningskraften operatoren selv bruker, som normalt er minimal sammenlignet med arbeidsmengdene den styrer.

Hva skjer hvis KEDA-operatoren selv går ned?
Eksisterende ScaledObject-ressurser og den tilhørende HPA-en fortsetter normalt å fungere en kort periode basert på sist kjente tilstand, men ingen nye skaleringsbeslutninger tas før operatoren er oppe igjen. Derfor bør KEDA-operatoren selv overvåkes med samme alvor som andre kritiske klyngekomponenter, og ikke behandles som et “sett og glem”-verktøy.