Auf dieser Seite wird erläutert, wie Sie GKE Dataplane V2 für GKE-Cluster (Google Kubernetes Engine) aktivieren und Fehler beheben.
Neue Autopilot-Cluster haben GKE Dataplane V2 in den Versionen 1.22.7-gke.1500 und höher und den Versionen 1.23.4-gke.1500 und höher aktiviert. Wenn bei der Verwendung von GKE Dataplane V2 Probleme auftreten, fahren Sie mit der Fehlerbehebung fort.
GKE-Cluster mit GKE Dataplane V2 erstellen
Sie können GKE Dataplane V2 aktivieren, wenn Sie neue Cluster mit GKE-Version 1.20.6-gke.700 und höher über die gcloud CLI oder die GKE API erstellen. Sie können GKE Dataplane V2 auch in der Vorschau aktivieren, wenn Sie neue Cluster mit GKE-Version 1.17.9 und höher erstellen.
Console
Führen Sie die folgenden Aufgaben aus, um einen neuen Cluster mit GKE Dataplane V2 zu erstellen:
Rufen Sie in der Google Cloud Console die Seite Kubernetes-Cluster erstellen auf.
Klicken Sie im Abschnitt „Netzwerk“ das Kästchen Dataplane V2 aktivieren an. Die Option „Kubernetes-Netzwerkrichtlinie aktivieren“ ist deaktiviert, wenn Sie „Dataplance V2 aktivieren“ auswählen, da die Durchsetzung von Netzwerkrichtlinien in GKE Dataplane V2 integriert ist.
Klicken Sie auf Erstellen.
gcloud
Erstellen Sie mit dem folgenden Befehl einen neuen Cluster mit GKE Dataplane V2.
gcloud container clusters create CLUSTER_NAME \
--enable-dataplane-v2 \
--enable-ip-alias \
--release-channel CHANNEL_NAME \
--location COMPUTE_LOCATION
Dabei gilt:
CLUSTER_NAME
: Der Name des neuen Clusters.CHANNEL_NAME
: Eine Release-Version, die die GKE-Version 1.20.6-gke.700 oder höher enthält. Wenn Sie keine Release-Version verwenden möchten, können Sie statt--release-channel
auch das Flag--cluster-version
verwenden und Version 1.20.6-gke.700 oder höher angeben.COMPUTE_LOCATION
: der Compute Engine-Standort für den neuen Cluster.
API
Zum Erstellen eines neuen Clusters mit GKE Dataplane V2 geben Sie das Feld datapathProvider
im Objekt networkConfig
in der Anfrage create
für den Cluster an.
Das folgende JSON-Snippet zeigt die Konfiguration, die zum Aktivieren von GKE Dataplane V2 benötigt wird:
"cluster":{
"initialClusterVersion":"VERSION",
"ipAllocationPolicy":{
"useIpAliases":true
},
"networkConfig":{
"datapathProvider":"ADVANCED_DATAPATH"
},
"releaseChannel":{
"channel":"CHANNEL_NAME"
}
}
Dabei gilt:
- VERSION ist Ihre Clusterversion, die die Version GKE 1.20.6-gke.700 oder höher haben muss.
- CHANNEL_NAME ist eine Release-Version, die die GKE-Version 1.20.6-gke.700 oder höher enthält.
Fehlerbehebung bei GKE Dataplane V2
In diesem Abschnitt erfahren Sie, wie Sie Probleme mit GKE Dataplane V2 untersuchen und beheben.
Prüfen Sie, ob GKE Dataplane V2 aktiviert ist:
kubectl -n kube-system get pods -l k8s-app=cilium -o wide
Wenn GKE Dataplane V2 ausgeführt wird, enthält die Ausgabe Pods mit dem Präfix
anetd-
. anetd ist der Netzwerkcontroller für GKE Dataplane V2.Wenn das Problem bei Diensten oder der Durchsetzung von Netzwerkrichtlinien auftritt, prüfen Sie die
anetd
-Pod-Logs. Verwenden Sie in Cloud Logging die folgende Logauswahl:resource.type="k8s_container" labels."k8s-pod/k8s-app"="cilium" resource.labels.cluster_name="CLUSTER_NAME"
Wenn die Pod-Erstellung fehlschlägt, suchen Sie in den Kubelet-Logs nach Hinweisen. Verwenden Sie in Cloud Logging die folgende Logauswahl:
resource.type="k8s_node" log_name=~".*/logs/kubelet" resource.labels.cluster_name="CLUSTER_NAME"
Ersetzen Sie
CLUSTER_NAME
durch den Namen des Clusters oder entfernen Sie ihn vollständig, um Logs für alle Cluster anzuzeigen.Wenn die
anetd
-Pods nicht ausgeführt werden, prüfen Sie die ConfigMap „cilium-config“ auf Änderungen. Vermeiden Sie es, vorhandene Felder in dieser ConfigMap zu ändern, da solche Änderungen den Cluster destabilisieren undanetd
beeinträchtigen können. Die ConfigMap wird nur dann in den Standardzustand zurückgesetzt, wenn ihr neue Felder hinzugefügt werden. Änderungen an vorhandenen Feldern werden nicht zurückgepatcht. Wir empfehlen, den ConfigMap nicht zu ändern oder anzupassen.
Bekannte Probleme
Intermittierende Verbindungsprobleme im Zusammenhang mit NodePort
-Bereichskonflikten in GKE Dataplane V2-Clustern
In GKE Dataplane V2-Clustern können intermittierende Verbindungsprobleme bei maskiertem Traffic oder bei der Verwendung von temporären Ports auftreten. Diese Probleme sind auf potenzielle Portkonflikte mit dem reservierten Bereich NodePort
zurückzuführen und treten in der Regel in den folgenden Szenarien auf:
Benutzerdefiniert;
ip-masq-agent
Wenn Sie eine benutzerdefinierteip-masq-agent
(Version 2.10 oder höher) verwenden, für die der ClusterNodePort
- oder Load Balancer-Dienste hat, können aufgrund von Konflikten mit demNodePort
-Bereich sporadische Verbindungsprobleme auftreten. Seit Version 2.10 ist inip-masq-agent
das Argument--random-fully
standardmäßig intern implementiert. Um dieses Problem zu umgehen, legen Sie explizit--random-fully=false
(gilt seit Version 2.11) unter Argumenten in Ihrerip-masq-agent
-Konfiguration fest. Weitere Informationen zur Konfiguration finden Sie unter IP-Masquerade-Agent in Standardclustern konfigurieren.Sitzungsspezifische Überschneidung im Portbereich:Wenn sich der von
net.ipv4.ip_local_port_range
auf Ihren GKE-Knoten definierte sitzungsspezifische Portbereich mit demNodePort
-Bereich (30000–32767) überschneidet, kann dies auch Verbindungsprobleme auslösen. Achten Sie darauf, dass sich diese beiden Bereiche nicht überschneiden, um dieses Problem zu vermeiden.
Prüfen Sie die Konfiguration von ip-masq-agent
und die Einstellungen für den Bereich der temporären Ports, um sicherzustellen, dass sie nicht mit dem Bereich von NodePort
in Konflikt stehen. Wenn Sie zeitweise Verbindungsprobleme haben, sollten Sie diese möglichen Ursachen in Betracht ziehen und Ihre Konfiguration entsprechend anpassen.
Verbindungsprobleme mit hostPort
in GKE Dataplane V2-Clustern
Betroffene GKE-Versionen:1.29 und höher
In Clustern, die GKE Dataplane V2 verwenden, kann es zu Verbindungsfehlern kommen, wenn der Traffic auf die IP-Adresse eines Knotens gerichtet ist, wobei der Port der hostPort
ist, die im Pod definiert ist. Diese Probleme treten in zwei Hauptszenarien auf:
Knoten mit
hostPort
hinter einem Passthrough-Network-Load-Balancer:hostPort
bindet einen Pod an den Port eines bestimmten Knotens und ein Passthrough Network Load Balancer verteilt den Traffic auf alle Knoten. Wenn Sie Pods überhostPort
und einen Passthrough Network Load Balancer für das Internet freigeben, sendet der Load-Balancer möglicherweise Traffic an einen Knoten, auf dem der Pod nicht ausgeführt wird, was zu Verbindungsfehlern führt. Dies liegt an einer bekannten Einschränkung in GKE Dataplane V2, bei der der Traffic von Passthrough-Network Load Balancern nicht immer anhostPort
-Pods weitergeleitet wird.Problemumgehung:Wenn Sie
hostPort
eines Pods auf dem Knoten mit einem Passthrough-Network Load Balancer bereitstellen, geben Sie die interne oder externe IP-Adresse des Network Load Balancers im FeldhostIP
des Pods an.ports: - containerPort: 62000 hostPort: 62000 protocol: TCP hostIP: 35.232.62.64 - containerPort: 60000 hostPort: 60000 protocol: TCP hostIP: 35.232.62.64 # Assuming 35.232.62.64 is the external IP address of a passthrough Network Load Balancer.
hostPort
-Konflikt mit reserviertemNodePort
-Bereich:Wenn der
hostPort
eines Pods mit dem reserviertenNodePort
-Bereich (30000–32767) in Konflikt steht, kann Cilium den Traffic möglicherweise nicht an den Pod weiterleiten. Dieses Verhalten wurde in Clusterversionen 1.29 und höher beobachtet, da Cilium jetzthostPort
-Funktionen verwaltet und die vorherige Portmap-Methode ersetzt. Dies ist ein erwartetes Verhalten für Cilium und wird in der öffentlichen Dokumentation erwähnt.
Wir planen nicht, diese Einschränkungen in späteren Versionen zu beheben. Die Ursache dieser Probleme hängt mit dem Verhalten von Cilium zusammen und liegt außerhalb des direkten Einflussbereichs von GKE.
Empfehlung:Wir empfehlen, zu NodePort
-Diensten anstelle von hostPort
zu migrieren, um die Zuverlässigkeit zu verbessern. NodePort
– Die Dienste bieten ähnliche Funktionen.
Portbereiche für Netzwerkrichtlinien werden nicht wirksam
Wenn Sie in einer Netzwerkrichtlinie ein Feld vom Typ endPort
in einem Cluster angeben, für den GKE Dataplane V2 aktiviert ist, wird dies nicht wirksam.
Ab GKE 1.22 können Sie mit der Kubernetes Network Policy API einen Portbereich angeben, an dem die Netzwerkrichtlinie erzwungen wird. Diese API wird in Clustern mit Calico Network Policy unterstützt, aber nicht in Clustern mit GKE Dataplane V2.
Sie können das Verhalten Ihrer NetworkPolicy
-Objekte prüfen, indem Sie sie zurücklesen, nachdem sie auf den API-Server geschrieben wurden. Wenn das Objekt noch das Feld endPort
enthält, wird die Funktion erzwungen. Wenn das Feld endPort
fehlt, wird die Funktion nicht erzwungen. In allen Fällen ist das auf dem API-Server gespeicherte Objekt die "Source of Truth" für die Netzwerkrichtlinie.
Weitere Informationen finden Sie unter KEP-2079: Netzwerkrichtlinie zur Unterstützung von Portbereichen.
Pods zeigen failed to allocate for range 0: no IP addresses available in range set
-Fehlermeldung an
Betroffene GKE-Versionen: 1.22 bis 1.25
Bei GKE-Clustern, auf denen Knotenpools ausgeführt werden, die containerd verwenden und GKE Dataplane V2 aktiviert ist, kann es zu Problemen bei IP-Adressenlecks kommen. Außerdem können alle Pod-IP-Adressen auf einem Knoten erschöpft sein. Ein Pod, der auf einem betroffenen Knoten geplant ist, zeigt eine Fehlermeldung ähnlich der folgenden an:
failed to allocate for range 0: no IP addresses available in range set: 10.48.131.1-10.48.131.62
Weitere Informationen zu dem Problem finden Sie unter Containerd-Problem 5768.
Feste Versionen
Aktualisieren Sie Ihren Cluster auf eine der folgenden GKE-Versionen, um dieses Problem zu beheben:
- 1.22.17-gke.3100 oder höher.
- 1.23.16-gke.200 oder höher.
- 1.24.9-gke.3200 oder höher.
- 1.25.6-gke.200 oder höher.
Problemumgehungen für GKE-Standardcluster
Sie können dieses Problem beheben, indem Sie die gehackten Pod-IP-Adressen für den Knoten löschen.
Zum Löschen der gehackten Pod-IP-Adressen rufen Sie die Anmeldedaten für die Authentifizierung für den Cluster ab und führen die folgenden Schritte aus, um einen einzelnen Knoten zu bereinigen, wenn Sie seinen Namen kennen.
Speichern Sie das folgende Shell-Script in einer Datei mit dem Namen
cleanup.sh
:for hash in $(sudo find /var/lib/cni/networks/gke-pod-network -iregex '/var/lib/cni/networks/gke-pod-network/[0-9].*' -exec head -n1 {} \;); do hash="${hash%%[[:space:]]}"; if [ -z $(sudo ctr -n k8s.io c ls | grep $hash | awk '{print $1}') ]; then sudo grep -ilr $hash /var/lib/cni/networks/gke-pod-network; fi; done | sudo xargs -r rm
Führen Sie das Script auf einem Clusterknoten aus:
gcloud compute ssh --zone "ZONE" --project "PROJECT" NODE_NAME --command "$(cat cleanup.sh)"
Ersetzen Sie
NODE_NAME
durch den Namen des Knotens.
Sie können auch eine DaemonSet-Version dieses Skripts ausführen, die parallel auf allen Knoten ausgeführt wird:
Speichern Sie folgendes Manifest in einer Datei mit dem Namen
cleanup-ips.yaml
:apiVersion: apps/v1 kind: DaemonSet metadata: name: cleanup-ipam-dir namespace: kube-system spec: selector: matchLabels: name: cleanup-ipam template: metadata: labels: name: cleanup-ipam spec: hostNetwork: true securityContext: runAsUser: 0 runAsGroup: 0 containers: - name: cleanup-ipam image: gcr.io/gke-networking-test-images/ubuntu-test:2022 command: - /bin/bash - -c - | while true; do for hash in $(find /hostipam -iregex '/hostipam/[0-9].*' -mmin +10 -exec head -n1 {} \; ); do hash="${hash%%[[:space:]]}" if [ -z $(ctr -n k8s.io c ls | grep $hash | awk '{print $1}') ]; then grep -ilr $hash /hostipam fi done | xargs -r rm echo "Done cleaning up /var/lib/cni/networks/gke-pod-network at $(date)" sleep 120s done volumeMounts: - name: host-ipam mountPath: /hostipam - name: host-ctr mountPath: /run/containerd volumes: - name: host-ipam hostPath: path: /var/lib/cni/networks/gke-pod-network - name: host-ctr hostPath: path: /run/containerd
Führen Sie das Daemonset auf dem Cluster aus:
kubectl apply -f cleanup-ips.yaml
Sie müssen als Administrator des Clusters Zugriff auf kubectl haben, um diesen Befehl auszuführen.
Prüfen Sie die Logs des ausgeführten DaemonSets:
kubectl -n kube-system logs -l name=cleanup-ipam
Netzwerkrichtlinie bricht eine Verbindung aufgrund einer falschen Verbindungsverfolgung ab
Wenn ein Client-Pod über einen Dienst oder die virtuelle IP-Adresse eines internen Passthrough-Network Load Balancer eine Verbindung zu sich selbst herstellt, wird das Antwortpaket aufgrund eines falschen Conntrack-Lookups in der Datenebene nicht als Teil einer vorhandenen Verbindung identifiziert. Das bedeutet, dass eine Netzwerkrichtlinie, die eingehenden Traffic für den Pod einschränkt, für das Paket falsch erzwungen wird.
Die Auswirkungen dieses Problems hängen von der Anzahl der konfigurierten Pods für den Dienst ab. Wenn der Service beispielsweise einen Backend-Pod hat, schlägt die Verbindung immer fehl. Wenn der Service zwei Backend-Pods hat, schlägt die Verbindung in 50 % der Fälle fehl.
Feste Versionen
Aktualisieren Sie Ihren Cluster auf eine der folgenden GKE-Versionen, um dieses Problem zu beheben:
- 1.28.3-gke.1090000 oder höher
Problemumgehungen
Sie können dieses Problem mindern, indem Sie port
und containerPort
im Service-Manifest auf denselben Wert festlegen.
Paketdrops für Hairpin-Anschlussflows
Wenn ein Pod mithilfe eines Service eine TCP-Verbindung zu sich selbst erstellt, sodass der Pod sowohl Quelle als auch Ziel der Verbindung ist, überwacht die GKE Dataplane V2 eBPF-Verbindungsüberwachung den Verbindungsstatus nicht korrekt, was zu verlorenen conntrack-Einträgen führt.
Wenn ein Verbindungstupel (Protokoll, Quell-/Ziel-IP und Quell-/Zielport) offengelegt wurde, kann es bei neuen Verbindungen mit demselben Verbindungstupel dazu kommen, dass Rückgabepakete verworfen werden.
Feste Versionen
Aktualisieren Sie Ihren Cluster auf eine der folgenden GKE-Versionen, um dieses Problem zu beheben:
- 1.28.3-gke.1090000 oder höher
- 1.27.11-gke.1097000 oder höher
Problemumgehungen
Versuchen Sie einen der folgenden Schritte, um das Problem zu umgehen:
Aktivieren Sie die TCP-Wiederverwendung (Keep-Alives) für Anwendungen, die in Pods ausgeführt werden und möglicherweise über einen Service mit sich selbst kommunizieren. Dadurch wird verhindert, dass das TCP FIN-Flag ausgegeben wird und dass der Conntrack-Eintrag ausgegeben wird.
Wenn Sie kurzlebige Verbindungen verwenden, machen Sie den Pod über einen Proxy-Load-Balancer wie Gateway verfügbar, um den Dienst verfügbar zu machen. Dies führt dazu, dass das Ziel der Verbindungsanfrage auf die IP-Adresse des Load-Balancers festgelegt wird. Dadurch wird verhindert, dass GKE Dataplane V2 SNAT zum Loopback der IP-Adresse ausführt.
Upgrade der GKE-Steuerungsebene führt zu anetd
-Pod-Deadlock
Wenn Sie ein Upgrade eines GKE-Cluster mit aktiviertem GKE Dataplane V2 (erweiterter Datenpfad) von Version 1.27 auf Version 1.28 durchführen, kann es zu einer Deadlock-Situation kommen. Arbeitslasten können aufgrund der Unfähigkeit, alte Pods zu beenden oder erforderliche Komponenten wie anetd
zu planen, zu Unterbrechungen führen.
Ursache
Beim Cluster-Upgrade-Prozess steigt der Ressourcenbedarf für die GKE Dataplane V2-Komponenten. Diese Erhöhung kann zu Ressourcenkonflikten führen, die die Kommunikation zwischen dem Cilium CNI-Plug-in (Container Network Interface) und dem Cilium-Daemon unterbrechen.
Symptome
Möglicherweise treten die folgenden Symptome auf:
anetd
Pods bleiben im StatusPending
hängen.- Arbeitslast-Pods bleiben im Status
Terminating
hängen. - Fehler, die auf Kommunikationsfehler bei Cilium hinweisen, z. B.
failed to connect to Cilium daemon
. Fehler beim Bereinigen von Netzwerkressourcen für Pod-Sandboxes, z. B.:
1rpc error: code = Unknown desc = failed to destroy network for sandbox "[sandbox_id]": plugin type="cilium-cni" failed (delete): unable to connect to Cilium daemon... connection refused
Problemumgehung
Standardcluster: Um das Problem zu beheben und die Planung des anetd
-Pods zu ermöglichen, erhöhen Sie vorübergehend die zuweisbaren Ressourcen auf dem betroffenen Knoten.
Führen Sie den folgenden Befehl aus, um den betroffenen Knoten zu ermitteln und die zuweisbare CPU und den zuweisbaren Arbeitsspeicher zu prüfen:
kubectl get nodes $NODE_NAME -o json | jq '.status.allocatable | {cpu, memory}'
Führen Sie den folgenden Befehl aus, um die zuweisbare CPU und den zuweisbaren Arbeitsspeicher vorübergehend zu erhöhen:
kubectl patch
Autopilot-Cluster: Um das Deadlock-Problem in Autopilot-Clustern zu beheben, geben Sie Ressourcen frei, indem Sie den betroffenen Pod erzwingen:
kubectl delete pod POD_NAME -n NAMESPACE --grace-period=0 --force
Ersetzen Sie Folgendes:
POD_NAME
: der Name des PodsNAMESPACE
: der Namespace des Pods.
Nachdem Sie die zuweisbaren Ressourcen auf dem Knoten erhöht haben und das Upgrade von GKE-Version 1.27 auf 1.28 abgeschlossen ist, wird der anetd
-Pod in der neueren Version ausgeführt.
Nächste Schritte
- Verwenden Sie die Logging von Netzwerkrichtlinien, um aufzuzeichnen, wann Verbindungen zu Pods von den Netzwerkrichtlinien Ihres Clusters zugelassen oder verweigert werden.
- Mehr über die Funktionsweise von GKE Dataplane V2 erfahren.