BLOG | NGINX

NGINX-Tutorial: Schützen Sie Kubernetes-APIs mit Rate Limiting

NGINX-Teil-von-F5-horiz-schwarz-Typ-RGB
Daniele Polencic Miniaturbild
Daniele Polencic
Veröffentlicht am 21. März 2022

Dieses Tutorial ist eines von vier, die Konzepte aus „Microservices March 2022“ in die Praxis umsetzen: Kubernetes-Netzwerk :

Möchten Sie detaillierte Anleitungen zur Verwendung von NGINX für noch mehr Anwendungsfälle von Kubernetes-Netzwerken? Laden Sie unser kostenloses E-Book „Verwaltung des Kubernetes-Verkehrs mit NGINX“ herunter: Ein praktischer Leitfaden .

Ihre Organisation hat gerade ihre erste App und API in Kubernetes gestartet. Man hat Ihnen mitgeteilt, dass mit einem hohen Datenverkehr zu rechnen ist (und hat bereits eine automatische Skalierung implementiert, um sicherzustellen, dass der NGINX Ingress Controller den Datenverkehr schnell weiterleiten kann), es gibt jedoch Bedenken, dass die API das Ziel eines böswilligen Angriffs sein könnte. Wenn die API eine große Menge an HTTP-Anfragen empfängt – was bei Brute-Force-Angriffen zum Erraten von Passwörtern oder bei DDoS-Angriffen möglich ist –, sind sowohl die API als auch die App möglicherweise überlastet oder stürzen sogar ab.

Aber Sie haben Glück! Bei der als Rate Limiting bezeichneten Verkehrssteuerungstechnik handelt es sich um einen API-Gateway-Anwendungsfall, der die Rate eingehender Anfragen auf einen für echte Benutzer typischen Wert begrenzt. Sie konfigurieren den NGINX Ingress Controller, um eine Ratenbegrenzungsrichtlinie zu implementieren, die verhindert, dass die App und die API durch zu viele Anfragen überlastet werden. Gute Arbeit!

Übersicht über Labor und Tutorial

Dieser Blog begleitet das Labor für Einheit 2 von Microservices März 2022 – Verfügbarmachen von APIs in Kubernetes und zeigt, wie mehrere NGINX-Ingress-Controller mit Ratenbegrenzung kombiniert werden, um eine Überlastung von Apps und APIs zu verhindern.

Zum Ausführen des Lernprogramms benötigen Sie einen Computer mit:

  • 2 CPUs oder mehr
  • 2 GB freier Speicher
  • 20 GB freier Speicherplatz
  • Internetverbindung
  • Container- oder Virtual Machine Manager, wie etwa Docker, Hyperkit, Hyper-V, KVM, Parallels, Podman, VirtualBox oder VMware Fusion/Workstation
  • Minikube installiert
  • Helm installiert
  • Eine Konfiguration, die Ihnen das Öffnen eines Browserfensters ermöglicht. Ist dies nicht möglich, muss nach einer Möglichkeit gesucht werden, über einen Browser auf die entsprechenden Dienste zuzugreifen.

Um den größtmöglichen Nutzen aus dem Labor und dem Lernprogramm zu ziehen, empfehlen wir Ihnen, vor dem Beginn Folgendes zu tun:

In diesem Tutorial werden die folgenden Technologien verwendet:

Die Anweisungen für jede Herausforderung enthalten den vollständigen Text der YAML-Dateien, die zum Konfigurieren der Apps verwendet werden. Sie können den Text auch aus unserem GitHub-Repository kopieren. Zusammen mit dem Text jeder YAML-Datei wird ein Link zu GitHub bereitgestellt.

Dieses Tutorial umfasst drei Herausforderungen:

  1. Bereitstellen eines Clusters, einer App, einer API und eines Ingress-Controllers
  2. Überfordern Sie Ihre App und API
  3. Speichern Sie Ihre App und API mit Dual Ingress Controllern und Rate Limiting

Herausforderung 1: Bereitstellen eines Clusters, einer App, einer API und eines Ingress-Controllers

In dieser Challenge stellen Sie einen Minikube-Cluster bereit und installieren Podinfo als Beispiel-App und API. Anschließend stellen Sie den NGINX Ingress Controller bereit , konfigurieren die Verkehrsführung und testen die Ingress-Konfiguration .

Erstellen eines Minikube-Clusters

Erstellen Sie einen Minikube- Cluster. Nach einigen Sekunden bestätigt eine Meldung, dass die Bereitstellung erfolgreich war.

$ minikube start 🏄 Fertig! kubectl ist jetzt so konfiguriert, dass es standardmäßig den Cluster „minikube“ und den Namespace „default“ verwendet 

Installieren Sie die Podinfo-App und die Podinfo-API

Podinfo ist eine „mit Go erstellte Webanwendung, die Best Practices zum Ausführen von Microservices in Kubernetes demonstriert“. Aufgrund seines geringen Platzbedarfs verwenden wir es als Beispiel-App und API.

  1. Erstellen Sie mit einem Texteditor Ihrer Wahl eine YAML-Datei namens 1-apps.yaml mit dem folgenden Inhalt (oder kopieren Sie sie von GitHub ). Es definiert eine Bereitstellung, die Folgendes umfasst:

    • Eine Webanwendung (wir nennen sie Podinfo Frontend ), die eine HTML-Seite rendert
    • Eine API ( Podinfo API ), die eine JSON-Nutzlast zurückgibt
    API-Version: Apps/v1
    Art: Bereitstellung 
    Metadaten: 
    Name: API 
    Spezifikation: 
    Selektor: 
    MatchLabels: 
    App: API 
    Vorlage: 
    Metadaten: 
    Labels: 
    App: API 
    Spezifikation: 
    Container: 
    -Name: API 
    Bild: stefanprodan/podinfo 
    Ports: 
    -ContainerPort: 9898 
    --- 
    API-Version: v1 
    Art: Dienst 
    Metadaten: 
    Name: API 
    Spezifikation: 
    Ports: 
    -Port: 80 
    ZielPort: 9898 
    KnotenPort: 30001 
    Selektor: 
    App: API 
    Typ: LoadBalancer 
    --- 
    API-Version: Apps/v1 
    Art: Bereitstellung 
    Metadaten: 
    Name: Frontend 
    Spezifikation: 
    Selektor: 
    MatchLabels: 
    App: Frontend 
    Vorlage: 
    Metadaten: 
    Labels: 
    App: Frontend 
    Spezifikation: 
    Container: 
    - Name: Frontend 
    Bild: stefanprodan/podinfo 
    Ports: 
    - ContainerPort: 9898 
    --- 
    API-Version: v1 
    Art: Dienst 
    Metadaten: 
    Name: Frontend 
    Spezifikation: 
    Ports: 
    -Port: 80 
    ZielPort: 9898 
    KnotenPort: 30002 
    Selektor: 
    App: Frontend 
    Typ: Lastenausgleich
    
  2. Stellen Sie die App und die API bereit:

    $ kubectl apply -f 1-apps.yaml deployment.apps/api erstellt service/api erstellt deployment.apps/frontend erstellt service/frontend erstellt 
    
  3. Bestätigen Sie, dass die Pods für die Podinfo-API und das Podinfo-Frontend erfolgreich bereitgestellt wurden, wie durch den Wert „Wird ausgeführt“ in der Spalte „STATUS“ angezeigt.

    $ kubectl get pods NAME BEREIT STATUS NEUSTART ALTER api-7574cf7568-c6tr6 1/1 Läuft 0 87s frontend-6688d86fc6-78qn7 1/1 Läuft 0 87s 
    
    
    

Bereitstellen des NGINX Ingress Controllers

Am schnellsten lässt sich NGINX Ingress Controller mit Helm installieren.

Installieren Sie NGINX Ingress Controller mit Helm in einem separaten Namespace ( nginx ).

  1. Erstellen Sie den Namespace:

    $ kubectl erstelle Namespace nginx 
    
  2. Fügen Sie das NGINX-Repository zu Helm hinzu:

    $ helm repo add nginx-stable https://helm.nginx.com/stable 
    
  3. Laden Sie NGINX Ingress Controller herunter und installieren Sie es in Ihrem Cluster:

    $ helm install main nginx-stable/nginx-ingress \ --set controller.watchIngressWithoutClass=true \ --set controller.ingressClass=nginx \ --set controller.service.type=NodePort \ --set controller.service.httpPort.nodePort=30010 \ --set controller.enablePreviewPolicies=true \ --namespace nginx 
    
  4. Bestätigen Sie, dass der NGINX Ingress Controller-Pod bereitgestellt wurde. Dies wird durch den Wert „Running“ in der Spalte „STATUS“ angezeigt (der Lesbarkeit halber ist die Ausgabe auf zwei Zeilen verteilt).

    $ kubectl get pods -namespace nginx NAME BEREIT STATUS ... main-nginx-ingress-779b74bb8b-d4qtc 1/1 Wird ausgeführt ... ... STARTET DAS ALTER NEU ... 0,92 Sek. 
    

Leiten Sie den Datenverkehr an Ihre App weiter

  1. Erstellen Sie mit einem Texteditor Ihrer Wahl eine YAML-Datei namens 2-ingress.yaml mit dem folgenden Inhalt (oder kopieren Sie sie von GitHub ). Es definiert das Ingress-Manifest, das zum Weiterleiten des Datenverkehrs an die App und API erforderlich ist.
  2. API-Version: networking.k8s.io/v1
    Art: Ingress 
    Metadaten: 
    Name: Vorname 
    Spezifikation: 
    IngressClassName: nginx 
    Regeln: 
    - Host: „example.com“ 
    http: 
    Pfade: 
    - Backend: 
    Dienst: 
    Name: Frontend 
    Port: 
    Nummer: 80 
    Pfad: / 
    Pfadtyp: Präfix 
    - Host: "api.example.com" 
    http: 
    Pfade: 
    - Backend: 
    Dienst: 
    Name: API 
    Port: 
    Nummer: 80 
    Pfad: / 
    Pfadtyp: Präfix
    
  3. Stellen Sie die Ingress-Ressource bereit:
  4. $ kubectl apply -f 2-ingress.yaml ingress.networking.k8s.io/zuerst erstellt 
    

Testen der Ingress-Konfiguration

  1. Um sicherzustellen, dass Ihre Ingress-Konfiguration wie erwartet funktioniert, testen Sie sie mit einem temporären Pod. Starten Sie einen verfügbaren BusyBox- Pod im Cluster:

    $ kubectl run -ti --rm=true busybox --image=busybox Wenn keine Eingabeaufforderung angezeigt wird, drücken Sie die Eingabetaste. / #
    
  2. Testen Sie die Podinfo-API , indem Sie eine Anfrage an den NGINX Ingress Controller-Pod mit dem Hostnamen api.example.com senden. Die angezeigte Ausgabe zeigt an, dass die API Datenverkehr empfängt.

    / # wget --header="Host: api.example.com" -qO- main-nginx-ingress.nginx { "Hostname": "api-687fd448f8-t7hqk", "Version": "6.0.3", "Revision": "", "Farbe": "#34577c", "Logo": "https://raw.githubusercontent.com/stefanprodan/podinfo/gh-pages/cuddle_clap.gif", "Nachricht": "Grüße von Podinfo v6.0.3", "goos": "Linux", "goarch": "arm64", "Runtime": "go1.16.9", "num_goroutine": "6", "num_cpu": "4" } 
    
  3. Testen Sie das Podinfo-Frontend, indem Sie den folgenden Befehl im selben BusyBox-Pod ausführen, um einen Webbrowser zu simulieren und die Webseite abzurufen. Die angezeigte Ausgabe ist der HTML-Code für den Start der Webseite.
    / # wget --header="Host: beispiel.com" --header="User-Agent: Mozilla" -qO- main-nginx-ingress.nginx <!DOCTYPE html> 
    <html> 
    <head> 
    <title>frontend-596d5c9ff4-xkbdc</title> 
    # ...
    
  4. Öffnen Sie Podinfo in einem anderen Terminal in einem Browser. Die Begrüßungsseite von Podinfo zeigt an, dass Podinfo ausgeführt wird.

    $ Minikube-Dienst Podinfo
    

    Glückwunsch! NGINX Ingress Controller empfängt Anfragen und leitet sie an die App und API weiter.

  5. Beenden Sie die BusyBox-Sitzung im ursprünglichen Terminal:

    / # beenden $
    

Herausforderung 2: Überfordern Sie Ihre App und API

Bei dieser Herausforderung installieren Sie Locust , ein Open-Source-Tool zur Lastgenerierung, und simulieren damit einen Verkehrsanstieg , der die API überlastet und zum Absturz der App führt.

Installieren Sie Locust

  1. Erstellen Sie mit einem Texteditor Ihrer Wahl eine YAML-Datei namens 3-locust.yaml mit dem folgenden Inhalt (oder kopieren Sie sie von GitHub ).

    Das ConfigMap- Objekt definiert ein Skript namens locustfile.py , das Anfragen generiert, die mit den richtigen Headern an den Pod gesendet werden. Der Datenverkehr ist nicht gleichmäßig zwischen der App und der API verteilt – die Anfragen werden verzerrt an die Podinfo-API weitergeleitet, wobei nur 1 von 5 Anfragen an das Podinfo-Frontend geht.

    Die Bereitstellungs- und Serviceobjekte definieren den Locust-Pod.

    API-Version: v1
    Art: ConfigMap 
    metadata: 
    name: locust-script 
    data: 
    locustfile.py: |- 
    from locust import HttpUser, task, between 
    
    class QuickstartUser(HttpUser): 
    wait_time = between(0.7, 1.3) 
    
    @task(1) 
    def visit_website(self): 
    with self.client.get("/", headers={"Host": "example.com", "User-Agent": "Mozilla"}, timeout=0.2, catch_response=True) als Antwort: 
    if response.request_meta["response_time"] > 200: 
    response.failure("Frontend fehlgeschlagen") 
    sonst: 
    response.success() 
    
    @task(5) 
    def visit_api(self): 
    with self.client.get("/", headers={"Host": "api.example.com"}, timeout=0.2) als Antwort: 
    if response.request_meta["response_time"] > 200: 
    response.failure("API fehlgeschlagen") 
    sonst: 
    response.success() 
    --- 
    apiVersion: apps/v1 
    kind: Bereitstellung 
    Metadaten: 
    Name: locust 
    Spezifikation: 
    Selektor: 
    MatchLabels: 
    App: locust 
    Vorlage: 
    Metadaten: 
    Labels: 
    App: locust 
    Spezifikation: 
    Container: 
    - Name: locust 
    Bild: locustio/locust 
    Ports: 
    - ContainerPort: 8089 
    volumeMounts: 
    - mountPath: /home/locust 
    Name: locust-script 
    volumes: 
    - Name: locust-script 
    configMap: 
    Name: locust-script 
    --- 
    apiVersion: v1 
    kind: Dienst 
    Metadaten: 
    Name: locust 
    Spezifikation: 
    Ports: 
    -Port: 8089 
    ZielPort: 8089 
    KnotenPort: 30015 
    Selektor: 
    App: Heuschrecke 
    Typ: Lastenausgleich
    
  2. Locust einsetzen:

    $ kubectl apply -f 3-locust.yaml configmap/locust-script erstellt deployment.apps/locust erstellt service/locust erstellt 
    
  3. Überprüfen Sie die Locust-Bereitstellung. In der folgenden Beispielausgabe wurde der Überprüfungsbefehl nur wenige Sekunden nach dem Befehl „kubectl apply ausgeführt und die Installation ist daher noch im Gange, wie durch den Wert „ContainerCreating“ für den Locust-Pod im Feld „STATUS“ angezeigt. Warten Sie, bis der Wert „Running“ lautet, bevor Sie mit dem nächsten Abschnitt fortfahren. (Die Ausgabe ist der Lesbarkeit halber auf zwei Zeilen verteilt.)
    $ kubectl get pods NAME BEREIT STATUS ... api-7574cf7568-c6tr6 1/1 Wird ausgeführt ... frontend-6688d86fc6-78qn7 1/1 Wird ausgeführt ... locust-77c699c94d-hc76t 0/1 Container wird erstellt ... ... STARTET DAS ALTER NEU ... 0,33 m ... 0,33 m ... 0 4 Sekunden
    

Simulieren Sie einen Verkehrsanstieg

  1. Öffnen Sie Locust in einem Browser.

    $ Minikube-Dienst Heuschrecke
    
  2. Geben Sie in die Felder folgende Werte ein:

    • Anzahl der Benutzer1000
    • Spawnrate30
    • Hosthttp://main-nginx-ingress
  3. Klicken Sie auf die Schaltfläche „Swarming starten“, um Datenverkehr an die Podinfo-API und das Podinfo-Frontend zu senden. Beobachten Sie die Verkehrsmuster auf den Registerkarten „Locust -Diagramme“ und „Fehler“ :

    • Diagramm – Mit zunehmender Anzahl der API-Anfragen verschlechtern sich die Antwortzeiten der Podinfo-API .
    • Fehler – Da sich Podinfo API und Podinfo Frontend einen Ingress-Controller teilen, führt die steigende Anzahl von API-Anfragen bald dazu, dass die Web-App Fehler zurückgibt.

Dies ist problematisch, da ein einzelner böswilliger Akteur, der die API verwendet, nicht nur die API, sondern alle vom NGINX Ingress Controller bereitgestellten Apps lahmlegen kann!

Herausforderung 3: Speichern Sie Ihre App und API mit Dual Ingress Controllern und Rate Limiting

In der letzten Herausforderung stellen Sie zwei NGINX Ingress Controller bereit, um die Einschränkungen der vorherigen Bereitstellung zu beseitigen, indem Sie für jeden einen separaten Namespace erstellen , separate NGINX Ingress Controller-Instanzen für Podinfo Frontend und Podinfo API installieren, Locust neu konfigurieren, um den Datenverkehr für die App und API an ihre jeweiligen NGINX Ingress Controller weiterzuleiten , und überprüfen, ob die Ratenbegrenzung wirksam ist . Sehen wir uns zunächst an, wie das Architekturproblem angegangen werden kann. In der vorherigen Herausforderung haben Sie den NGINX Ingress Controller mit API-Anfragen überlastet, was sich auch auf die App auswirkte. Dies geschah, weil ein einzelner Ingress Controller für die Weiterleitung des Datenverkehrs sowohl an die Web-App ( Podinfo Frontend ) als auch an die API ( Podinfo API ) verantwortlich war.

Durch Ausführen eines separaten NGINX Ingress Controller-Pods für jeden Ihrer Dienste wird verhindert, dass Ihre App durch zu viele API-Anfragen beeinträchtigt wird. Dies ist nicht unbedingt für jeden Anwendungsfall erforderlich, aber in unserer Simulation lassen sich die Vorteile des Ausführens mehrerer NGINX Ingress Controller leicht erkennen.

Der zweite Teil der Lösung, der eine Überlastung der Podinfo-API verhindert, besteht in der Implementierung einer Ratenbegrenzung durch die Verwendung des NGINX Ingress Controller als API-Gateway.

 

Was ist Ratenbegrenzung?

Durch die Ratenbegrenzung wird die Anzahl der Anfragen begrenzt, die ein Benutzer in einem bestimmten Zeitraum stellen kann. Um beispielsweise einen DDoS-Angriff abzuschwächen, können Sie mithilfe der Ratenbegrenzung die Rate eingehender Anfragen auf einen für echte Benutzer typischen Wert begrenzen. Wenn die Ratenbegrenzung mit NGINX implementiert wird, werden Clients, die zu viele Anfragen senden, auf eine Fehlerseite umgeleitet, damit sie die API nicht negativ beeinflussen können. Wie das funktioniert, erfahren Sie in der NGINX Ingress Controller-Dokumentation .

Was ist ein API-Gateway?

Ein API-Gateway leitet API-Anfragen von Clients an die entsprechenden Dienste weiter. Eine große Fehlinterpretation dieser einfachen Definition besteht darin, dass ein API-Gateway eine einzigartige Technologie sei. Das ist es nicht. Vielmehr beschreibt „API-Gateway“ eine Reihe von Anwendungsfällen, die über verschiedene Arten von Proxys implementiert werden können – am häufigsten ein ADC oder Load Balancer und Reverse Proxy, zunehmend aber auch ein Ingress-Controller oder Service Mesh. Die Ratenbegrenzung ist ein häufiger Anwendungsfall für die Bereitstellung eines API-Gateways. Erfahren Sie mehr über Anwendungsfälle von API-Gateways in Kubernetes unter „Wie treffe ich eine Auswahl?“ API-Gateway vs. Ingress-Controller vs. Service Mesh auf unserem Blog.

Vorbereiten Ihres Clusters

Bevor Sie die neue Architektur und Ratenbegrenzung implementieren können, müssen Sie die vorherige NGINX Ingress Controller-Konfiguration löschen.

  1. Löschen Sie die NGINX Ingress Controller-Konfiguration:

     

    $ kubectl delete -f 2-ingress.yaml ingress.networking.k8s.io "first" gelöscht 
    
    
    
  2. Erstellen Sie einen Namespace namens nginx‑web für das Podinfo-Frontend :

    $ kubectl create namespace nginx-web namespace/nginx-web erstellt 
    
    
    
  3. Erstellen Sie einen Namespace namens nginx‑api für die Podinfo API :

    $ kubectl create namespace nginx-api namespace/nginx-api erstellt 
    
    
    

Installieren Sie den NGINX Ingress Controller für das Podinfo-Frontend

  1. Installieren Sie den NGINX Ingress Controller:

    $ helm installiere web nginx-stable/nginx-ingress --set controller.ingressClass=nginx-web \ --set controller.service.type=NodePort \ --set controller.service.httpPort.nodePort=30020 \ --namespace nginx-web
    
    
    
  2. Erstellen Sie ein Ingress-Manifest namens 4-ingress-web.yaml für das Podinfo-Frontend (oder kopieren Sie es von GitHub ).

    API-Version: k8s.nginx.org/v1 Art: Metadaten der Richtlinie: Name: Rate-Limit-Richtlinie, Spezifikation: RateLimit: Rate: 10r/s-Taste:${binary_remote_addr} Zonengröße: 10M --- API-Version: k8s.nginx.org/v1 Art: VirtualServer-Metadaten: Name: API-VS-Spezifikation: IngressClassName: Nginx-API-Host: API.example.com-Richtlinien: - Name: Rate-Limit-Richtlinie Upstreams: - Name: API-Dienst: API-Port: 80 Routen: - Pfad: / Aktion: Pass: API
  3. Stellen Sie das neue Manifest bereit:

    $ kubectl apply -f 4-ingress-web.yaml ingress.networking.k8s.io/frontend erstellt  
    
    
    

Locust neu konfigurieren

Konfigurieren Sie nun Locust neu und überprüfen Sie Folgendes:

  • Die Podinfo-API wird nicht überlastet.
  • Unabhängig davon, wie viele Anfragen an die Podinfo-API gesendet werden, gibt es keine Auswirkungen auf das Podinfo-Frontend .

Führen Sie diese Schritte aus:

  1. Ändern Sie das Locust-Skript so, dass:

    • Alle Anfragen an das Podinfo-Frontend werden an den nginx‑web NGINX Ingress Controller unter http://web-nginx-ingress.nginx-web weitergeleitet.
    • Alle Anfragen an die Podinfo API werden an den nginx‑api NGINX Ingress Controller unter http://api-nginx-ingress.nginx-api weitergeleitet.

    Da Locust nur eine einzige URL im Dashboard unterstützt, codieren Sie den Wert im Python-Skript fest mithilfe der YAML-Datei 6-locust.yaml mit dem folgenden Inhalt (oder kopieren Sie ihn von GitHub ). Notieren Sie sich die URLs in jeder Aufgabe .

    
    API-Version: v1 
    Art: ConfigMap 
    metadata: 
    name: locust-script 
    data: 
    locustfile.py: |- 
    from locust import HttpUser, task, between 
    
    class QuickstartUser(HttpUser): 
    wait_time = between(0.7, 1.3) 
    
    @task(1) 
    def visit_website(self): 
    with self.client.get("http://web-nginx-ingress.nginx-web/", headers={"Host": "example.com", "User-Agent": "Mozilla"}, timeout=0.2, catch_response=True) als Antwort: 
    if response.request_meta["response_time"] > 200: 
    response.failure("Frontend fehlgeschlagen") 
    sonst: 
    response.success() 
    
    @task(5) 
    def visit_api(self): 
    with self.client.get("http://api-nginx-ingress.nginx-api/", headers={"Host": "api.example.com"}, timeout=0.2) als Antwort: 
    if response.request_meta["response_time"] > 200: 
    response.failure("API fehlgeschlagen") 
    sonst: 
    response.success() 
    --- 
    apiVersion: apps/v1 
    kind: Bereitstellung 
    Metadaten: 
    Name: locust 
    Spezifikation: 
    Selektor: 
    MatchLabels: 
    App: locust 
    Vorlage: 
    Metadaten: 
    Labels: 
    App: locust 
    Spezifikation: 
    Container: 
    - Name: locust 
    Bild: locustio/locust 
    Ports: 
    - ContainerPort: 8089 
    volumeMounts: 
    - mountPath: /home/locust 
    Name: locust-script 
    volumes: 
    - Name: locust-script 
    configMap: 
    Name: locust-script 
    --- 
    apiVersion: v1 
    kind: Dienst 
    Metadaten: 
    Name: locust 
    Spezifikation: 
    Ports: 
    -Port: 8089 
    ZielPort: 8089 
    KnotenPort: 30015 
    Selektor: 
    App: Heuschrecke 
    Typ: Lastenausgleich 
    
    
    
  2. Stellen Sie die neue Locust-Konfiguration bereit. Die Ausgabe bestätigt, dass das Skript geändert wurde, die anderen Elemente jedoch unverändert bleiben.

    $ kubectl apply -f 6-locust.yaml configmap/locust-script konfiguriert deployment.apps/locust unverändert service/locust unverändert
    
    
    
  3. Löschen Sie den Locust-Pod, um ein Neuladen der neuen ConfigMap zu erzwingen. Um den zu entfernenden Pod zu identifizieren, wird das Argument des Befehls „kubectl delete pod als Pipe-Befehle ausgedrückt, die den Locust-Pod aus der Liste aller Pods auswählen.

    $ kubectl lösche Pod `kubectl hole Pods | grep locust | awk {'print $1'}` 
    
    
    
  4. Überprüfen Sie, ob Locust neu geladen wurde (der Wert für den Locust-Pod in der Spalte „AGE“ beträgt nur wenige Sekunden).

    $ kubectl get pods NAME BEREIT STATUS ... api-7574cf7568-jrlvd 1/1 Wird ausgeführt ... frontend-6688d86fc6-vd856 1/1 Wird ausgeführt ... locust-77c699c94d-6chsg 0/1 Wird ausgeführt ... ... STARTET DAS ALTER NEU ... 0,9 Min. 57 Min. ... 0,9 Min. 57 Min. ... 0 6 Sekunden
    
    
    

Überprüfen der Ratenbegrenzung

  1. Kehren Sie zu Locust zurück und ändern Sie die Parameter in diesen Feldern:

    • Anzahl der Benutzer400
    • Spawnrate10
    • Hosthttp://main-nginx-ingress
  2. Klicken Sie auf die Schaltfläche „Swarming starten“, um Datenverkehr an die Podinfo-API und das Podinfo-Frontend zu senden.

    Beobachten Sie, wie in der Titelleiste von Locust oben links mit der steigenden Anzahl von Benutzern in der Spalte „STATUS“ auch der Wert in der Spalte „FEHLER“ steigt. Allerdings stammen die Fehler nicht mehr vom Podinfo-Frontend, sondern von der Podinfo-API, da aufgrund der für die API festgelegten Ratenbegrenzung zu viele Anfragen abgelehnt werden. In der Ablaufverfolgung unten rechts können Sie sehen, dass NGINX die Nachricht zurückgibt503 Dienst vorübergehend nicht verfügbar , was Teil der Ratenbegrenzungsfunktion ist und angepasst werden kann. Die API ist geschwindigkeitsbegrenzt und die Webanwendung ist immer verfügbar. Gut gemacht!

Nächste Schritte

In der Praxis reicht eine Ratenbegrenzung allein nicht aus, um Ihre Apps und APIs vor böswilligen Akteuren zu schützen. Sie müssen mindestens eine oder zwei der folgenden Methoden zum Schutz von Kubernetes-Apps, -APIs und -Infrastruktur implementieren:

  • Authentifizierung und Autorisierung
  • Web Application Firewall und DDoS-Schutz
  • Ende-zu-Ende-Verschlüsselung und Zero Trust
  • Einhaltung von Branchenvorschriften

Diese und weitere Themen behandeln wir in Einheit 3 von Microservices März 2022 – Microservices-Sicherheitsmuster in Kubernetes . Um NGINX Ingress Controller für Kubernetes mit NGINX Plus und NGINX App Protect auszuprobieren, starten Sie noch heute Ihre kostenlose 30-Tage-Testversion oder kontaktieren Sie uns, um Ihre Anwendungsfälle zu besprechen . Um NGINX Ingress Controller mit NGINX Open Source auszuprobieren, können Sie den Quellcode der Version abrufen oder einen vorgefertigten Container von DockerHub herunterladen.


„Dieser Blogbeitrag kann auf Produkte verweisen, die nicht mehr verfügbar und/oder nicht mehr unterstützt werden. Die aktuellsten Informationen zu verfügbaren F5 NGINX-Produkten und -Lösungen finden Sie in unserer NGINX-Produktfamilie . NGINX ist jetzt Teil von F5. Alle vorherigen NGINX.com-Links werden auf ähnliche NGINX-Inhalte auf F5.com umgeleitet."