Kubernetes: ignorierte Einstellungen für das Pod-Räumungs-Timeout

Erstellt am 27. Feb. 2019  ·  15Kommentare  ·  Quelle: kubernetes/kubernetes

Bitte verwenden Sie diese Vorlage, während Sie einen Fehler melden, und geben Sie so viele Informationen wie möglich an. Wenn Sie dies nicht tun, wird Ihr Fehler möglicherweise nicht rechtzeitig behoben. Vielen Dank! Wenn die Angelegenheit sicherheitsrelevant ist, geben Sie sie bitte privat über https://kubernetes.io/security/ weiter.

Was ist passiert? Ich habe die pod-eviction-timeout -Einstellungen von kube-controller-manager auf dem Masterknoten geändert (um die Zeit zu verkürzen, bevor k8s bei einem Knotenausfall einen Pod neu erstellt). Der Standardwert ist 5 Minuten, ich habe 30 Sekunden konfiguriert. Mit dem Befehl sudo docker ps --no-trunc | grep "kube-controller-manager" ich überprüft, ob die Änderung erfolgreich angewendet wurde:

kubeadmin<strong i="10">@nodetest21</strong>:~$ sudo docker ps --no-trunc | grep "kube-controller-manager"
387261c61ee9cebce50de2540e90b89e2bc710b4126a0c066ef41f0a1fb7cf38   sha256:0482f640093306a4de7073fde478cf3ca877b6fcc2c4957624dddb2d304daef5                         "kube-controller-manager --address=127.0.0.1 --authentication-kubeconfig=/etc/kubernetes/controller-manager.conf --authorization-kubeconfig=/etc/kubernetes/controller-manager.conf --client-ca-file=/etc/kubernetes/pki/ca.crt --cluster-signing-cert-file=/etc/kubernetes/pki/ca.crt --cluster-signing-key-file=/etc/kubernetes/pki/ca.key --controllers=*,bootstrapsigner,tokencleaner --kubeconfig=/etc/kubernetes/controller-manager.conf --leader-elect=true --requestheader-client-ca-file=/etc/kubernetes/pki/front-proxy-ca.crt --root-ca-file=/etc/kubernetes/pki/ca.crt --service-account-private-key-file=/etc/kubernetes/pki/sa.key --use-service-account-credentials=true --pod-eviction-timeout=30s" 

Ich habe eine Basisbereitstellung mit zwei Replikaten angewendet:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: busybox
  namespace: default
spec:
  replicas: 2
  selector:
    matchLabels:
      app: busybox
  template:
    metadata:
      labels:
        app: busybox
    spec:
      containers:
      - image: busybox
        command:
        - sleep
        - "3600"
        imagePullPolicy: IfNotPresent
        name: busybox
      restartPolicy: Always

Der erste Pod, der auf dem ersten Worker-Knoten erstellt wurde, der zweite Pod, der auf dem zweiten Worker-Knoten erstellt wurde:

NAME         STATUS   ROLES    AGE   VERSION
nodetest21   Ready    master   34m   v1.13.3
nodetest22   Ready    <none>   31m   v1.13.3
nodetest23   Ready    <none>   30m   v1.13.3

NAMESPACE     NAME                                 READY   STATUS    RESTARTS   AGE   IP          NODE         NOMINATED NODE   READINESS GATES
default       busybox-74b487c57b-5s6g7             1/1     Running   0          13s   10.44.0.2   nodetest22   <none>           <none>
default       busybox-74b487c57b-6zdvv             1/1     Running   0          13s   10.36.0.1   nodetest23   <none>           <none>
kube-system   coredns-86c58d9df4-gmcjd             1/1     Running   0          34m   10.32.0.2   nodetest21   <none>           <none>
kube-system   coredns-86c58d9df4-wpffr             1/1     Running   0          34m   10.32.0.3   nodetest21   <none>           <none>
kube-system   etcd-nodetest21                      1/1     Running   0          33m   10.0.1.4    nodetest21   <none>           <none>
kube-system   kube-apiserver-nodetest21            1/1     Running   0          33m   10.0.1.4    nodetest21   <none>           <none>
kube-system   kube-controller-manager-nodetest21   1/1     Running   0          20m   10.0.1.4    nodetest21   <none>           <none>
kube-system   kube-proxy-6mcn8                     1/1     Running   1          31m   10.0.1.5    nodetest22   <none>           <none>
kube-system   kube-proxy-dhdqj                     1/1     Running   0          30m   10.0.1.6    nodetest23   <none>           <none>
kube-system   kube-proxy-vqjg8                     1/1     Running   0          34m   10.0.1.4    nodetest21   <none>           <none>
kube-system   kube-scheduler-nodetest21            1/1     Running   1          33m   10.0.1.4    nodetest21   <none>           <none>
kube-system   weave-net-9qls7                      2/2     Running   3          31m   10.0.1.5    nodetest22   <none>           <none>
kube-system   weave-net-h2cb6                      2/2     Running   0          33m   10.0.1.4    nodetest21   <none>           <none>
kube-system   weave-net-vkb62                      2/2     Running   0          30m   10.0.1.6    nodetest23   <none>           <none>

Um die korrekte Pod-Räumung zu testen, habe ich den ersten Worker-Knoten heruntergefahren. Nach ~ 1 min änderte sich dann der Status des ersten Worker-Knotens in "NotReady"
Ich musste +5 Minuten warten (dies ist das Standardzeitlimit für die Pod-Räumung), bis der Pod auf dem ausgeschalteten Knoten auf dem anderen Knoten neu erstellt wurde.

Was Sie erwartet hatten :
Nachdem der Knotenstatus "NotReady" gemeldet hat, sollte der Pod nach 30 Sekunden auf dem anderen Knoten neu erstellt werden, wenn die Standardeinstellung 5 Minuten beträgt!

Wie man es reproduziert (so minimal und präzise wie möglich) :
Erstellen Sie drei Knoten. Initialisieren Sie Kubernetes auf dem ersten Knoten ( sudo kubeadm init ), wenden Sie das Netzwerk-Plugin ( kubectl apply -f "https://cloud.weave.works/k8s/net?k8s-version=$(kubectl version | base64 | tr -d '\n')" ) an und verbinden Sie dann die beiden anderen Knoten (z. B. kubeadm join 10.0.1.4:6443 --token xdx9y1.z7jc0j7c8g8lpjog --discovery-token-ca-cert-hash sha256:04ae8388f607755c14eed702a23fd47802d5512e092b08add57040a2ae0736ac ).
Fügen Sie dem Kube Controller Manager auf dem Masterknoten den Parameter pod-eviction-timeout hinzu: sudo vi /etc/kubernetes/manifests/kube-controller-manager.yaml :

apiVersion: v1
kind: Pod
metadata:
  annotations:
    scheduler.alpha.kubernetes.io/critical-pod: ""
  creationTimestamp: null
  labels:
    component: kube-controller-manager
    tier: control-plane
  name: kube-controller-manager
  namespace: kube-system
spec:
  containers:
  - command:
    - kube-controller-manager
    - --address=127.0.0.1
    - --authentication-kubeconfig=/etc/kubernetes/controller-manager.conf
    - --authorization-kubeconfig=/etc/kubernetes/controller-manager.conf
    - --client-ca-file=/etc/kubernetes/pki/ca.crt
    - --cluster-signing-cert-file=/etc/kubernetes/pki/ca.crt
    - --cluster-signing-key-file=/etc/kubernetes/pki/ca.key
    - --controllers=*,bootstrapsigner,tokencleaner
    - --kubeconfig=/etc/kubernetes/controller-manager.conf
    - --leader-elect=true
    - --requestheader-client-ca-file=/etc/kubernetes/pki/front-proxy-ca.crt
    - --root-ca-file=/etc/kubernetes/pki/ca.crt
    - --service-account-private-key-file=/etc/kubernetes/pki/sa.key
    - --use-service-account-credentials=true
    - --pod-eviction-timeout=30s

(Das Yaml ist abgeschnitten, hier wird nur der zugehörige erste Teil angezeigt.)

Überprüfen Sie, ob die Einstellungen angewendet wurden:
sudo docker ps --no-trunc | grep "kube-controller-manager"

Wenden Sie eine Bereitstellung mit zwei Replikaten an und überprüfen Sie, ob ein Pod auf dem ersten Worker-Knoten und der zweite auf dem zweiten Worker-Knoten erstellt wurde.
Fahren Sie einen der Knoten herunter und überprüfen Sie die zwischen dem Ereignis verstrichene Zeit, wenn der Knoten "NotReady" meldet und der Pod neu erstellt wird.

Was müssen wir noch wissen? ::
Ich habe das gleiche Problem auch in einer Multi-Master-Umgebung.

Umwelt :

  • Kubernetes-Version (verwenden Sie kubectl version ): v1.13.3
    Client-Version: version.Info {Major: "1", Minor: "13", GitVersion: "v1.13.3", GitCommit: "721bfa751924da8d1680787490c54b9179b1fed0", GitTreeState: "clean", BuildDate: "2019-02-01T20: 08: 12Z ", GoVersion:" go1.11.5 ", Compiler:" gc ", Plattform:" linux / amd64 "}
    Serverversion: version.Info {Major: "1", Minor: "13", GitVersion: "v1.13.3", GitCommit: "721bfa751924da8d1680787490c54b9179b1fed0", GitTreeState: "clean", BuildDate: "2019-02-01T20: 00: 57Z ", GoVersion:" go1.11.5 ", Compiler:" gc ", Plattform:" linux / amd64 "}
  • Cloud-Anbieter oder Hardwarekonfiguration: Azure VM
  • Betriebssystem (z. B. cat /etc/os-release ): NAME = "Ubuntu" VERSION = "16.04.5 LTS (Xenial Xerus)"
  • Kernel (zB uname -a ): Linux nodetest21 4.15.0-1037-azure # 39 ~ 16.04.1-Ubuntu SMP Di Jan 15 17:20:47 UTC 2019 x86_64 x86_64 x86_64 GNU / Linux
  • Tools installieren:
  • Andere: Docker v18.06.1-ce
kinbug siapps sinode

Hilfreichster Kommentar

Vielen Dank für Ihr Feedback ChiefAlexander!
Das ist die Situation, die Sie geschrieben haben. Ich habe die Pods überprüft und sichergestellt, dass dem Pod die Standardwerte für die Toleranz zugewiesen sind:

kubectl describe pod busybox-74b487c57b-95b6n | grep -i toleration -A 2
Tolerations:     node.kubernetes.io/not-ready:NoExecute for 300s
                 node.kubernetes.io/unreachable:NoExecute for 300s

Also habe ich der Bereitstellung einfach meine eigenen Werte hinzugefügt:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: busybox
  namespace: default
spec:
  replicas: 2
  selector:
    matchLabels:
      app: busybox
  template:
    metadata:
      labels:
        app: busybox
    spec:
      tolerations:
      - key: "node.kubernetes.io/unreachable"
        operator: "Exists"
        effect: "NoExecute"
        tolerationSeconds: 2
      - key: "node.kubernetes.io/not-ready"
        operator: "Exists"
        effect: "NoExecute"
        tolerationSeconds: 2
      containers:
      - image: busybox
        command:
        - sleep
        - "3600"
        imagePullPolicy: IfNotPresent
        name: busybox
      restartPolicy: Always

Nach dem Anwenden der Bereitstellung bei einem Knotenausfall ändert sich der Knotenstatus in "NotReady" und die Pods werden nach 2 Sekunden neu erstellt.

Wir müssen uns also nicht mehr mit Pod-Räumungs-Timeout befassen, das Timeout kann auf Pod-Basis eingestellt werden! Cool!

Danke nochmal für deine Hilfe!

Alle 15 Kommentare

@ kubernetes / sig-node-bugs
@ kubernetes / sig-apps-bugs

@danielloczi : Wiederholen Sie die Erwähnungen, um eine Benachrichtigung auszulösen:
@ kubernetes / sig-node-bugs, @ kubernetes / sig-apps-bugs

Als Antwort darauf :

@ kubernetes / sig-node-bugs
@ kubernetes / sig-apps-bugs

Anweisungen zur Interaktion mit mir mithilfe von PR-Kommentaren finden Sie hier . Wenn Sie Fragen oder Vorschläge zu meinem Verhalten haben, reichen Sie bitte ein Problem mit dem Repository

Ich bin auch auf dieses Problem gestoßen, als ich getestet habe, wie das Räumungszeitlimit niedriger eingestellt wurde. Nachdem ich mich einige Zeit damit beschäftigt hatte, stellte ich fest, dass die Ursache die neuen TaintBasedEvictions sind.

In Version 1.13 wird die TaintBasedEvictions-Funktion auf Beta hochgestuft und standardmäßig aktiviert. Daher werden die Taints automatisch vom NodeController (oder Kubelet) hinzugefügt und die normale Logik zum Entfernen von Pods von Knoten basierend auf der Ready NodeCondition ist deaktiviert.

Wenn Sie das Feature-Flag dafür auf false setzen, werden Pods wie erwartet entfernt. Ich habe mir keine Zeit genommen, um den auf Taint basierenden Räumungscode zu durchsuchen, aber ich würde vermuten, dass wir dieses Flag für das Räumungszeitlimit nicht verwenden.

Ich schaue mir das genauer an. Wenn TaintBasedEvictions auf true gesetzt ist, können Sie die Räumungszeit Ihrer Pods unter den angegebenen Bedingungen unter den angegebenen Bedingungen einstellen:
https://kubernetes.io/docs/concepts/configuration/taint-and-toleration/#taint -based-evictions
Die Standardwerte hierfür werden von einem Zulassungscontroller festgelegt: https://github.com/kubernetes/kubernetes/blob/master/plugin/pkg/admission/defaulttolerationseconds/admission.go#L34
Diese beiden Flags können über den Kube-Apiserver gesetzt werden und sollten den gleichen Effekt erzielen.

// Controller will not proactively sync node health, but will monitor node
// health signal updated from kubelet. There are 2 kinds of node healthiness
// signals: NodeStatus and NodeLease. NodeLease signal is generated only when
// NodeLease feature is enabled. If it doesn't receive update for this amount
// of time, it will start posting "NodeReady==ConditionUnknown". The amount of
// time before which Controller start evicting pods is controlled via flag
// 'pod-eviction-timeout'.
// Note: be cautious when changing the constant, it must work with
// nodeStatusUpdateFrequency in kubelet and renewInterval in NodeLease
// controller. The node health signal update frequency is the minimal of the
// two.
// There are several constraints:
// 1. nodeMonitorGracePeriod must be N times more than  the node health signal
//    update frequency, where N means number of retries allowed for kubelet to
//    post node status/lease. It is pointless to make nodeMonitorGracePeriod
//    be less than the node health signal update frequency, since there will
//    only be fresh values from Kubelet at an interval of node health signal
//    update frequency. The constant must be less than podEvictionTimeout.
// 2. nodeMonitorGracePeriod can't be too large for user experience - larger
//    value takes longer for user to see up-to-date node health.

Vielen Dank für Ihr Feedback ChiefAlexander!
Das ist die Situation, die Sie geschrieben haben. Ich habe die Pods überprüft und sichergestellt, dass dem Pod die Standardwerte für die Toleranz zugewiesen sind:

kubectl describe pod busybox-74b487c57b-95b6n | grep -i toleration -A 2
Tolerations:     node.kubernetes.io/not-ready:NoExecute for 300s
                 node.kubernetes.io/unreachable:NoExecute for 300s

Also habe ich der Bereitstellung einfach meine eigenen Werte hinzugefügt:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: busybox
  namespace: default
spec:
  replicas: 2
  selector:
    matchLabels:
      app: busybox
  template:
    metadata:
      labels:
        app: busybox
    spec:
      tolerations:
      - key: "node.kubernetes.io/unreachable"
        operator: "Exists"
        effect: "NoExecute"
        tolerationSeconds: 2
      - key: "node.kubernetes.io/not-ready"
        operator: "Exists"
        effect: "NoExecute"
        tolerationSeconds: 2
      containers:
      - image: busybox
        command:
        - sleep
        - "3600"
        imagePullPolicy: IfNotPresent
        name: busybox
      restartPolicy: Always

Nach dem Anwenden der Bereitstellung bei einem Knotenausfall ändert sich der Knotenstatus in "NotReady" und die Pods werden nach 2 Sekunden neu erstellt.

Wir müssen uns also nicht mehr mit Pod-Räumungs-Timeout befassen, das Timeout kann auf Pod-Basis eingestellt werden! Cool!

Danke nochmal für deine Hilfe!

@danielloczi Hallo danielloczi, wie behebst du dieses Problem? Ich treffe auch dieses Problem

@ 323929 Ich denke, @danielloczi kümmert sich nicht um den Parameter pod-eviction-timeout im kube-controller-manager, sondern löst ihn mit Taint based Evictions , Ich habe mit Taint based Evictions getestet, es hat funktioniert für mich.

Das ist richtig: Ich habe einfach angefangen, Taint based Eviction .

Ist es möglich, es global zu machen? Ich möchte das nicht für jede Pod-Konfiguration aktivieren, insbesondere, dass ich viele vorbereitete Dinge vom Ruder aus verwende

+1 für die Möglichkeit, es für den gesamten Cluster zu konfigurieren. Die Optimierung pro Pod oder pro Bereitstellung ist selten sinnvoll: In den meisten Fällen ist ein vernünftiger globaler Wert bequemer, und der aktuelle Standardwert von 5 m ist in vielen Fällen zu lang.

Bitte, bitte öffnen Sie diese Ausgabe erneut.

Ich stehe vor dem gleichen Problem: Gibt es eine Möglichkeit, Taint-basierte Räumungen nicht zu aktivieren, und das Pod-Räumungs-Timeout funktioniert im globalen Modus?

Ich stehe vor dem gleichen Problem: Gibt es eine Möglichkeit, Taint-basierte Räumungen nicht zu aktivieren, und das Pod-Räumungs-Timeout funktioniert im globalen Modus?

Ich denke, dass Sie die globale Pod-Räumung über Apiserver konfigurieren können: https://kubernetes.io/docs/reference/command-line-tools-reference/kube-apiserver/
Ich habe dies nicht versucht, aber wie ich sehen kann, gibt es Optionen: - Standard-nicht-bereit-Toleranz-Sekunden und - Standard-nicht erreichbare-Toleranz-Sekunden.

Warum wurde dieser Fehler als geschlossen markiert? Es sieht so aus, als ob das ursprüngliche Problem nicht gelöst, sondern nur umgangen wird.
Mir ist nicht klar, warum das Flag für das Pod-Räumungs-Timeout nicht funktioniert

gleicher Fehler

War diese Seite hilfreich?
0 / 5 - 0 Bewertungen