Skalbarhet är ett nyckelkrav för molnapplikationer. Med Kubernetes är det lika enkelt att skala ett program som att öka antalet repliker för lämplig distribution eller ReplicaSet – men det är en manuell process.
Kubernetes tillåter att applikationer skalas automatiskt (d.v.s. Pods i en distribution eller ReplicaSet) på ett deklarativt sätt med hjälp av Horizontal Pod Autoscaler-specifikationen. Standardkriteriet för automatisk skalning är CPU-användningsmått (resursmått), men du kan integrera anpassade och externt tillhandahållna mätvärden.
Team Kubernetes aaS från Mail.ru översatt en artikel om hur man använder externa mätvärden för att automatiskt skala en Kubernetes-applikation. För att visa hur allt fungerar använder författaren HTTP-åtkomstbegäranmätningar, som samlas in med Prometheus.
Istället för horisontell autoskalning av poddar används Kubernetes Event Driven Autoscaling (KEDA), en Kubernetes-operatör med öppen källkod. Den integreras naturligt med Horizontal Pod Autoscaler för att ge sömlös autoskalning (inklusive till/från noll) för händelsedrivna arbetsbelastningar. Koden finns på GitHub.
Kort översikt över systemet
Diagrammet visar en kort beskrivning av hur allt fungerar:
Applikationen tillhandahåller HTTP-träffräkningsstatistik i Prometheus-format.
Prometheus är konfigurerad att samla in dessa mätvärden.
Prometheus scaler i KEDA är konfigurerad att automatiskt skala applikationen baserat på antalet HTTP-träffar.
Nu kommer jag att berätta i detalj om varje element.
KEDA och Prometheus
Prometheus är ett verktyg för övervakning och varning av öppen källkod, del Cloud Native Computing Foundation. Samlar in mätvärden från olika källor och lagrar dem som tidsseriedata. För att visualisera data kan du använda grafana eller andra visualiseringsverktyg som fungerar med Kubernetes API.
KEDA stöder konceptet med en skalare - den fungerar som en brygga mellan KEDA och det externa systemet. Implementeringen av skalare är specifik för varje målsystem och extraherar data från det. KEDA använder dem sedan för att styra automatisk skalning.
Skalare stöder flera datakällor, till exempel Kafka, Redis, Prometheus. Det vill säga, KEDA kan användas för att automatiskt skala Kubernetes-distributioner med hjälp av Prometheus-mått som kriterier.
Testapplikation
Golang-testapplikationen ger åtkomst via HTTP och utför två viktiga funktioner:
Använder Prometheus Go-klientbiblioteket för att instrumentera applikationen och tillhandahålla http_requests-måttet, som innehåller ett antal träffar. Slutpunkten där Prometheus-mätvärden är tillgänglig finns på URI:n /metrics.
var httpRequestsCounter = promauto.NewCounter(prometheus.CounterOpts{
Name: "http_requests",
Help: "number of http requests",
})
Som svar på en förfrågan GET applikationen ökar värdet på nyckeln (access_count) i Redis. Det här är ett enkelt sätt att utföra arbetet som en del av en HTTP-hanterare och även kontrollera Prometheus-mått. Det metriska värdet måste vara detsamma som värdet access_count i Redis.
Applikationen distribueras till Kubernetes via Deployment. En tjänst skapas också ClusterIP, gör det att Prometheus-servern kan få applikationsstatistik.
Skalaren fungerar som en brygga mellan KEDA och det externa systemet från vilket mätvärden måste erhållas. ScaledObject är en anpassad resurs som måste distribueras för att synkronisera distributionen med händelsekällan, i det här fallet Prometheus.
ScaledObject innehåller distributionsskalningsinformation, metadata för händelsekälla (som anslutningshemligheter, könamn), pollingintervall, återställningsperiod och annan data. Det resulterar i motsvarande autoskalningsresurs (HPA-definition) för att skala distributionen.
När ett föremål ScaledObject tas bort, raderas motsvarande HPA-definition.
Här är definitionen ScaledObject för vårt exempel använder den en skalare Prometheus:
Triggertyp - Prometheus. Prometheus-serveradressen nämns tillsammans med metriskt namn, tröskelvärde och PromQL-fråga, som kommer att användas. PromQL-fråga - sum(rate(http_requests[2m])).
Enligt pollingInterval,KEDA begär ett mål från Prometheus var femtonde sekund. Minst en under (minReplicaCount), och det maximala antalet kapslar inte överstiger maxReplicaCount (i detta exempel - tio).
Kan installeras minReplicaCount lika med noll. I det här fallet aktiverar KEDA noll-till-ett-distributionen och exponerar sedan HPA för ytterligare automatisk skalning. Den omvända ordningen är också möjlig, det vill säga skalning från ett till noll. I exemplet valde vi inte noll eftersom detta är en HTTP-tjänst och inte ett on-demand-system.
Magin inuti autoskalning
Tröskeln används som en utlösare för att skala distributionen. I vårt exempel är PromQL-frågan sum(rate (http_requests [2m])) returnerar den aggregerade HTTP-förfrågningsfrekvensen (förfrågningar per sekund), mätt under de senaste två minuterna.
Eftersom tröskelvärdet är tre betyder det att det kommer att vara en under medan värdet sum(rate (http_requests [2m])) mindre än tre. Om värdet ökar läggs ytterligare en sub till varje gång sum(rate (http_requests [2m])) ökar med tre. Till exempel, om värdet är från 12 till 14, då är antalet pods fyra.
Nu ska vi försöka ställa in det!
förinställning
Allt du behöver är ett Kubernetes-kluster och ett konfigurerat verktyg kubectl. Det här exemplet använder ett kluster minikube, men du kan ta vilken annan som helst. För att installera ett kluster finns det ledning.
helm init initierar det lokala kommandoradsgränssnittet och installerar även Tiller till Kubernetes-klustret.
kubectl get pods -n kube-system | grep tiller
Vänta tills Tiller-podden går in i körläge.
Översättarens anteckning: Författaren använder Helm@2, vilket kräver att Tiller-serverkomponenten är installerad. Nu är Helm@3 aktuellt, det kräver ingen serverdel.
Efter installation av Helm räcker ett kommando för att starta Redis:
kubectl apply -f prometheus.yaml
//output
clusterrole.rbac.authorization.k8s.io/prometheus created
serviceaccount/default configured
clusterrolebinding.rbac.authorization.k8s.io/prometheus created
configmap/prom-conf created
deployment.extensions/prometheus-deployment created
service/prometheus-service created
Kontrollera att allt har börjat:
kubectl get pods -l=app=prometheus-server
Vänta tills Prometheus går in i staten Running.
användning kubectl port-forward för att komma åt Prometheus användargränssnitt (eller API-server) på http://localhost:9090.
KEDA_POD_NAME=$(kubectl get pods -n keda
-o=jsonpath='{.items[0].metadata.name}')
kubectl logs $KEDA_POD_NAME -n keda
Resultatet ser ut ungefär så här:
time="2019-10-15T09:38:28Z" level=info msg="Watching ScaledObject:
default/prometheus-scaledobject"
time="2019-10-15T09:38:28Z" level=info msg="Created HPA with
namespace default and name keda-hpa-go-prom-app"
Kolla under ansökningar. En instans måste vara igång pga minReplicaCount är lika med 1:
kubectl get pods -l=app=go-prom-app
Verifiera att HPA-resursen skapades framgångsrikt:
kubectl get hpa
Du borde se något i stil med:
NAME REFERENCE TARGETS MINPODS MAXPODS REPLICAS AGE
keda-hpa-go-prom-app Deployment/go-prom-app 0/3 (avg) 1 10 1 45s
Hälsokontroll: applikationsåtkomst
För att komma åt vår applikations REST-slutpunkt, kör:
Du kan nu komma åt din Go-app med adressen http://localhost:8080. För att göra detta, kör kommandot:
curl http://localhost:8080/test
Resultatet ser ut ungefär så här:
Accessed on 2019-10-21 11:29:10.560385986 +0000 UTC
m=+406004.817901246
Access count 1
Vid denna tidpunkt kontrollera även Redis. Du kommer att se att nyckeln access_count ökat till 1:
kubectl exec -it redis-server-master-0 -- redis-cli get access_count
//output
"1"
Se till att det metriska värdet är http_requests det samma:
curl http://localhost:8080/metrics | grep http_requests
//output
# HELP http_requests number of http requests
# TYPE http_requests counter
http_requests 1
Lastskapande
Vi kommer använda hallå — verktyg för att generera last:
I detta fall är det faktiska resultatet 1,686057971014493 och visas i fältet value. Detta räcker inte för skalning, eftersom tröskeln vi anger är 3.
Mer belastning!
I den nya terminalen, övervaka antalet applikationsenheter:
kubectl get pods -l=app=go-prom-app -w
Låt oss öka belastningen med kommandot:
./hey -n 2000 http://localhost:8080/test
Efter ett tag kommer du att se HPA skala driftsättningen och lansera nya poddar. Kontrollera din HPA för att säkerställa att:
kubectl get hpa
NAME REFERENCE TARGETS MINPODS MAXPODS REPLICAS AGE
keda-hpa-go-prom-app Deployment/go-prom-app 1830m/3 (avg) 1 10 6 4m22s
Om belastningen är inkonsekvent kommer driftsättningen att reduceras till den punkt där endast en pod körs. Om du vill kontrollera det faktiska måttet (returneras av PromQL-frågan), använd sedan kommandot:
//Delete KEDA
kubectl delete namespace keda
//Delete the app, Prometheus server and KEDA scaled object
kubectl delete -f .
//Delete Redis
helm del --purge redis-server
Slutsats
Med KEDA kan du automatiskt skala dina Kubernetes-distributioner (till/från noll) baserat på data från externa mätvärden. Till exempel baserat på Prometheus-mått, kölängd i Redis, konsumentlatens i Kafka-ämnet.
KEDA integreras med en extern källa och tillhandahåller även dess mätvärden via Metrics Server till Horizontal Pod Autoscaler.