Utiliser APISIX, Prometheus et KEDA pour mettre à l'échelle les applications de manière élastique dans Kubernetes

Jintao Zhang

Jintao Zhang

February 17, 2023

Technology

Introduction

La quantité de trafic qui entre dans une application varie au fil du temps. Par exemple, une application de shopping en ligne est beaucoup plus sollicitée pendant la période des fêtes que les jours ordinaires. Pouvoir ajuster la capacité de l'application en fonction du trafic permettra d'offrir une bien meilleure expérience utilisateur et des services de qualité.

Apache APISIX est une passerelle API cloud-native haute performance qui peut fournir des métriques significatives pour déterminer si les applications doivent être mises à l'échelle. C'est un middleware qui traite tout le trafic envoyé aux applications en amont et peut donc collecter des données de trafic au cours du processus.

Pour réaliser une mise à l'échelle élastique, KEDA sera utilisé comme contrôleur, et Prometheus sera utilisé pour récupérer les métriques fournies par APISIX.

using KEDA for autocaling

Comment utiliser le Prometheus Scaler dans KEDA

KEDA est un autoscaler basé sur des événements dans Kubernetes, qui peut configurer divers scalers. Dans cet article, le Prometheus scaler sera utilisé pour obtenir les métriques exposées par APISIX.

Déployer KEDA

Le déploiement de KEDA est relativement simple, il suffit d'ajouter le dépôt Helm correspondant et de l'installer.

(MoeLove) ➜ helm repo add kedacore https://kedacore.github.io/charts "kedacore" a été ajouté à vos dépôts (MoeLove) ➜ helm repo update kedacore Patientez pendant que nous récupérons les dernières versions de vos dépôts de charts... ...Mise à jour réussie du dépôt de charts "kedacore" Mise à jour terminée. ⎈Bon Helm!⎈ (MoeLove) ➜ helm install keda kedacore/keda --namespace keda --create-namespace NAME: keda LAST DEPLOYED: Thu Jan 19 00:01:00 2023 NAMESPACE: keda STATUS: déployé REVISION: 1 TEST SUITE: Aucun

Après l'installation, le Pod a un statut Running, indiquant qu'il a été installé.

(MoeLove) ➜ kubectl -n keda get pods NAME READY STATUS RESTARTS AGE keda-operator-metrics-apiserver-6d4db7dcff-ck9qg 1/1 Running 0 36s keda-operator-5dd4748dcd-k8jjz 1/1 Running 0 36s

Déployer Prometheus

Ici, nous utilisons Prometheus Operator pour déployer Prometheus. Prometheus Operator peut nous aider à déployer rapidement l'instance Prometheus dans Kubernetes et à ajouter les règles de surveillance via une configuration déclarative.

Complétez l'installation de Prometheus Operator en suivant les étapes ci-dessous.

(MoeLove) ➜ https://github.com/prometheus-operator/prometheus-operator/releases/download/v0.62.0/bundle.yaml (MoeLove) ➜ kubectl apply --server-side -f bundle.yaml customresourcedefinition.apiextensions.k8s.io/alertmanagerconfigs.monitoring.coreos.com serverside-applied customresourcedefinition.apiextensions.k8s.io/alertmanagers.monitoring.coreos.com serverside-applied customresourcedefinition.apiextensions.k8s.io/podmonitors.monitoring.coreos.com serverside-applied customresourcedefinition.apiextensions.k8s.io/probes.monitoring.coreos.com serverside-applied customresourcedefinition.apiextensions.k8s.io/prometheuses.monitoring.coreos.com serverside-applied customresourcedefinition.apiextensions.k8s.io/prometheusrules.monitoring.coreos.com serverside-applied customresourcedefinition.apiextensions.k8s.io/servicemonitors.monitoring.coreos.com serverside-applied customresourcedefinition.apiextensions.k8s.io/thanosrulers.monitoring.coreos.com serverside-applied clusterrolebinding.rbac.authorization.k8s.io/prometheus-operator serverside-applied clusterrole.rbac.authorization.k8s.io/prometheus-operator serverside-applied deployment.apps/prometheus-operator serverside-applied serviceaccount/prometheus-operator serverside-applied service/prometheus-operator serverside-applied

Ensuite, utilisez la configuration suivante pour Prometheus et appliquez-la au cluster Kubernetes.

--- apiVersion: v1 kind: ServiceAccount metadata: name: prometheus --- apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRole metadata: name: prometheus rules: - apiGroups: [""] resources: - nodes - nodes/metrics - services - endpoints - pods verbs: ["get", "list", "watch"] - apiGroups: [""] resources: - configmaps verbs: ["get"] - apiGroups: - networking.k8s.io resources: - ingresses verbs: ["get", "list", "watch"] - nonResourceURLs: ["/metrics"] verbs: ["get"] --- apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRoleBinding metadata: name: prometheus roleRef: apiGroup: rbac.authorization.k8s.io kind: ClusterRole name: prometheus subjects: - kind: ServiceAccount name: prometheus namespace: default --- apiVersion: monitoring.coreos.com/v1 kind: Prometheus metadata: name: prometheus spec: serviceAccountName: prometheus serviceMonitorSelector: matchLabels: app: apisix serviceMonitorNamespaceSelector: matchLabels: team: apisix resources: requests: memory: 400Mi enableAdminAPI: false --- apiVersion: v1 kind: Service metadata: name: prometheus spec: type: LoadBalancer ports: - name: web port: 9090 protocol: TCP targetPort: web selector: prometheus: prometheus

Après avoir appliqué la configuration au cluster Kubernetes, vous pouvez voir qu'une instance Prometheus est créée dans le namespace default. Comme nous avons configuré Prometheus avec le TYPE LoadBalancer, les utilisateurs peuvent accéder directement à Prometheus via l'IP publique du LoadBalancer.

(MoeLove) ➜ kubectl get svc NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE kubernetes ClusterIP 10.43.0.1 <none> 443/TCP 96m prometheus-operator ClusterIP None <none> 8080/TCP 92m prometheus-operated ClusterIP None <none> 9090/TCP 41m prometheus LoadBalancer 10.43.125.194 216.6.66.66 9090:30099/TCP 41m

Comment déployer la passerelle API et activer la surveillance

Ensuite, déployez le contrôleur APISIX Ingress et utilisez Prometheus pour la collecte de métriques.

La méthode est similaire pour les utilisateurs qui utilisent uniquement APISIX au lieu du contrôleur APISIX Ingress. Nous ne l'expliquerons pas séparément ici.

Ici, Helm est utilisé pour le déploiement, et le contrôleur APISIX Ingress ainsi qu'APISIX peuvent être déployés simultanément dans le cluster.

(MoeLove) ➜ helm repo add apisix https://charts.apiseven.com "apisix" existe déjà avec la même configuration, ignoré (MoeLove) ➜ helm repo update apisix Patientez pendant que nous récupérons les dernières versions de vos dépôts de charts... ...Mise à jour réussie du dépôt de charts "apisix" Mise à jour terminée. ⎈Bon Helm!⎈ (MoeLove) ➜ helm upgrade --install apisix apisix/apisix --create-namespace --namespace apisix --set gateway.type=LoadBalancer --set ingress-controller.enabled=true --set ingress-controller.config.apisix.serviceNamespace=apisix Release "apisix" a été mis à niveau. Bon Helm! NAME: apisix LAST DEPLOYED: Thu Jan 19 02:11:23 2023 NAMESPACE: apisix STATUS: déployé REVISION: 1 TEST SUITE: Aucun NOTES: 1. Obtenez l'URL de l'application en exécutant ces commandes : NOTE : Cela peut prendre quelques minutes pour que l'IP du LoadBalancer soit disponible. Vous pouvez surveiller le statut en exécutant 'kubectl get --namespace apisix svc -w apisix-gateway' export SERVICE_IP=$(kubectl get svc --namespace apisix apisix-gateway --template "{{ range (index .status.loadBalancer.ingress 0) }}{{.}}{{ end }}") echo http://$SERVICE_IP:80

Ensuite, activez le plugin Prometheus d'APISIX. Veuillez vous référer aux deux documents suivants pour les méthodes de configuration spécifiques et les paramètres associés.

Une fois activé, Prometheus peut capturer les métriques exposées par APISIX en créant une ressource ServiceMonitor.

apiVersion: monitoring.coreos.com/v1 kind: ServiceMonitor metadata: name: example-app labels: app: apisix spec: selector: matchLabels: app: apisix endpoints: - port: web

Vérifier la capacité de mise à l'échelle élastique de l'application

Créez d'abord une application.

(MoeLove) ➜ kubectl create deploy httpbin --image=kennethreitz/httpbin --port=80 deployment.apps/httpbin créé (MoeLove) ➜ kubectl expose deploy httpbin --port 80

Créez les règles de routage suivantes et appliquez-les au cluster Kubernetes pour rediriger les requêtes via APISIX.

apiVersion: apisix.apache.org/v2 kind: ApisixRoute metadata: name: httpserver-route spec: http: - name: rule1 match: hosts: - local.httpbin.org paths: - /* backends: - serviceName: httpbin servicePort: 80

Ensuite, créez un ScaledObject KEDA et configurez les paramètres liés à Prometheus.

apiVersion: keda.sh/v1alpha1 kind: ScaledObject metadata: name: prometheus-scaledobject namespace: default spec: scaleTargetRef: name: httpbin triggers: - type: prometheus metadata: serverAddress: http://prometheus.default.svc:9090 metricName: apisix_http_status threshold: '10' query: sum(rate(apisix_http_status{route="httpserver-route"}[1m]))

La configuration ci-dessus signifie que sum(rate(apisix_http_status{route="httpserver-route"}[1m])) est utilisé comme expression de requête, et si le résultat atteint 10, l'expansion commencera. (La configuration ici est uniquement à des fins de démonstration, veuillez la modifier selon votre propre situation). Ensuite, nous effectuons des requêtes continues au service httpbin via curl.

Plus tard, si nous vérifions les pods de l'application, vous pouvez voir qu'elle a été mise à l'échelle automatiquement à deux par KEDA.

(MoeLove) ➜ kubectl get pods NAME READY STATUS RESTARTS AGE httpbin-d46d778d7-chtdw 1/1 Running 0 12m httpbin-d46d778d7-xanbj 1/1 Running 0 10s

Lorsque l'application reste inactive après un certain temps, nous constaterons que le nombre de pods a automatiquement diminué à une instance.

(MoeLove) ➜ kubectl get pods NAME READY STATUS RESTARTS AGE httpbin-d46d778d7-chtdw 1/1 Running 0 32m

Résumé

KEDA utilise Prometheus comme scaler pour collecter les métriques exposées par APISIX. Comme tout le trafic passe d'abord par APISIX, obtenir des statistiques côté APISIX sera beaucoup plus simple et pratique.

Lorsque le volume des requêtes métier augmente, l'application sera automatiquement mise à l'échelle, et lorsque le volume des requêtes métier diminue, l'application sera automatiquement réduite.

Cette méthode peut atténuer les opérations manuelles de mise à l'échelle/réduction dans de nombreux environnements de production pour garantir la meilleure expérience utilisateur.

Tags: