Shinyproxy: Rolling Update für Shinyproxy-Bereitstellung verursacht verwaiste Pods

Erstellt am 19. Aug. 2019  ·  7Kommentare  ·  Quelle: openanalytics/shinyproxy

Hallo, wenn es eine Änderung in application.yaml gibt und das fortlaufende Update ausgewählt wird (mit Replikaten auf 0 und dann wieder auf 1 gesetzt) ​​- hauptsächlich weil das neue Shinyproxy-Image aus dem Artefakt heruntergeladen werden muss - Alle früheren Pods, die waren die vom vorherigen Shinyproxy hochgesponnen wurden, werden als Zombies zurückgelassen

Fortpflanzen:

  • kubectl alles bekommen

NAME BEREIT STATUS STARTET DAS ALTER NEU
pod/shinyproxy-7f76d48c79-8x9hs 2/2 Laufen 0 41m

NAME TYP CLUSTER-IP EXTERNE-IP PORT(S) ALTER
service/shinyproxy NodePort 172.30.85.1918080:32094/TCP 40m

NAME GEWÜNSCHTER AKTUELLER VERFÜGBARER ALTER
deploy.apps/shinyproxy 1 1 1 1 41m

NAME GEWÜNSCHTES AKTUELLES BEREITSCHAFTSALTER
replicaset.apps/shinyproxy-7f76d48c79 1 1 1 41m

NAME HOST/PORT PFAD DIENSTE PORT BEENDIGUNG WILDCARD
route.route.openshift.io/shinyproxy Shinyproxy-aap.apps.cpaas.service.test ShinyproxyKeiner

  • Melden Sie sich bei der App an (in meinem Fall verwende ich LDAP-Authentifizierung und /app_direct/ für eine glänzende Anwendung (neuer Pod für die Anwendung wird gestartet) - wie erwartet

NAME BEREIT STATUS STARTET DAS ALTER NEU
pod/shinyproxy-7f76d48c79-8x9hs 2/2 Laufen 0 43m
pod/sp-pod-e7603441-03ba-470b-925a-22cfba1716de 1/1 Läuft 0 12s

NAME TYP CLUSTER-IP EXTERNE-IP PORT(S) ALTER
service/shinyproxy NodePort 172.30.85.1918080:32094/TCP 43m

NAME GEWÜNSCHTER AKTUELLER VERFÜGBARER ALTER
deploy.apps/shinyproxy 1 1 1 1 43m

NAME GEWÜNSCHTES AKTUELLES BEREITSCHAFTSALTER
replicaset.apps/shinyproxy-7f76d48c79 1 1 1 43m

NAME HOST/PORT PFAD DIENSTE PORT BEENDIGUNG WILDCARD
route.route.openshift.io/shinyproxy Shinyproxy-aap.apps.cpaas.service.test ShinyproxyKeiner

  • Nach dem Erstellen des neuen Shinyproxy-Image:

kubectl scale --replicas=0 Bereitstellung/shinyproxy
deploy.extensions/shinyproxy skaliert

kubectl scale --replicas=1 Bereitstellung/shinyproxy
deploy.extensions/shinyproxy skaliert

  • Neues Image wurde heruntergeladen, damit Shiny-Proxy und Container erstellt werden.

NAME BEREIT STATUS STARTET DAS ALTER NEU
pod/shinyproxy-7f76d48c79-l5fvw 0/2 ContainerErstellung 0 4s
pod/sp-pod-e7603441-03ba-470b-925a-22cfba1716de 1/1 Laufen 0 1m

NAME TYP CLUSTER-IP EXTERNE-IP PORT(S) ALTER
service/shinyproxy NodePort 172.30.85.1918080:32094/TCP 44m

NAME GEWÜNSCHTER AKTUELLER VERFÜGBARER ALTER
deploy.apps/shinyproxy 1 1 1 0 45m

NAME GEWÜNSCHTES AKTUELLES BEREITSCHAFTSALTER
replicaset.apps/shinyproxy-7f76d48c79 1 1 0 45m

NAME HOST/PORT PFAD DIENSTE PORT BEENDIGUNG WILDCARD
route.route.openshift.io/shinyproxy Shinyproxy-aap.apps.cpaas.service.test ShinyproxyKeiner

  • In diesem Stadium reagiert meine Webanwendung nicht - das einzige, was zu tun ist, ist, die Registerkarte/das Fenster zu schließen. Und der Pod (für die R-Anwendung) bleibt bestehen, sofern er nicht manuell gelöscht wird.

  • Auf den Pod, der Ressourcen verbraucht, kann nicht zugegriffen werden, da auf die neuen Dienstpunkte zur aktualisierten Bereitstellung und Anwendung nur über eine Route über den Dienst zugegriffen werden kann

  • Es ist auch sehr schwierig zu erkennen, welche der Pods veraltet sind, und manuell zu löschen

Hilfreichster Kommentar

Ich habe eine Lösung für dieses Problem gefunden. Dies ist eigentlich kein Problem in Shinyproxy oder Containerproxy, da die Spring Boot-App korrekt und ordnungsgemäß heruntergefahren wird.

Das Problem ist der Beiwagencontainer kubctl proxy . Für Kubernetes ist nicht klar, dass Containerproxy auf den Sidecar-Container angewiesen ist, um mit Kubernetes selbst zu kommunizieren. Bei einer neuen Bereitstellung sendet Kubernetes also SIGTERM sowohl an den Proxy als auch an den Sidecar-Container in allen alten Pods. Der Sidecar-Container wird sofort beendet und containerproxy kann nicht mit Kubernetes kommunizieren.

Ich habe gelesen, dass Kubernetes im Begriff ist, diese Start- und Shutdown-Abhängigkeiten in v1.18 zu lösen, wie hier dokumentiert:
https://github.com/kubernetes/enhancements/issues/753
https://banzaicloud.com/blog/k8s-sidecars/

Bis dahin gibt es eine einfache Problemumgehung, um die folgende Lebenszyklusanmerkung in den Sidecar-Container einzufügen:

          lifecycle:
            preStop:
              exec:
                command: ["sh", "-c", "sleep 5"] # wait 5 seconds to let shinyproxy remove the pods on graceful shutdown

Alle 7 Kommentare

Hallo @ramkumarg1

Wenn Shinyproxy ein SIGTERM-Signal empfängt (wenn die Bereitstellung herunterskaliert wird), sollte es ordnungsgemäß beendet werden, indem zuerst alle Anwendungs-Pods gestoppt werden. Möglicherweise müssen Sie die Nachfrist terminationGracePeriodSeconds in der Pod-Spezifikation erhöhen (Standard ist 30 Sekunden). Wenn Shinyproxy innerhalb dieses Zeitraums nicht beendet werden kann, erhält es ein SIGKILL und wird sofort beendet, wobei verwaiste Pods zurückbleiben. Mehr Infos hier: https://kubernetes.io/docs/concepts/containers/container-lifecycle-hooks/

Danke @dseynaev Ich habe die Bereitstellungsspezifikation geändert, um TerminationGracePeriodSeconds einzuschließen - aber es hat keinen Unterschied gemacht. Der Pod wurde sofort beendet – Vielleicht ist dieses Problem mit https://github.com/kubernetes/kubernetes/issues/47576 verknüpft, wo Spring Boot SIGTERM ordnungsgemäß handhaben muss?

spec:
  terminationGracePeriodSeconds : 180
  containers:
  - name: shinyproxy

Wir beobachten das gleiche Problem mit Zombie-Pods, und für uns löst die Einstellung der Nachfrist für die Kündigung dies auch nicht.

Ich habe das gleiche Problem und das wird von Shiny/Containerproxy bei der Beendigung protokolliert:

2020-01-30 10:56:56.785  INFO 1 --- [           main] e.o.c.ContainerProxyApplication          : Started ContainerProxyApplication in 39.115 seconds (JVM running for 43.619)
2020-01-30 10:57:01.374  INFO 1 --- [  XNIO-2 task-1] io.undertow.servlet                      : Initializing Spring FrameworkServlet 'dispatcherServlet'
2020-01-30 10:57:01.375  INFO 1 --- [  XNIO-2 task-1] o.s.web.servlet.DispatcherServlet        : FrameworkServlet 'dispatcherServlet': initialization started
2020-01-30 10:57:01.507  INFO 1 --- [  XNIO-2 task-1] o.s.web.servlet.DispatcherServlet        : FrameworkServlet 'dispatcherServlet': initialization completed in 131 ms
2020-01-30 10:57:26.275  INFO 1 --- [ XNIO-2 task-16] e.o.containerproxy.service.UserService   : User logged in [user: **]
2020-01-30 10:57:35.802  INFO 1 --- [  XNIO-2 task-3] e.o.containerproxy.service.ProxyService  : Proxy activated [user: ***] [spec: insight] [id: 9274ad33-665a-4d47-bab5-6c4b39a618b8]
2020-01-30 10:59:02.376  INFO 1 --- [       Thread-2] ConfigServletWebServerApplicationContext : Closing org.springframework.boot.web.servlet.context.AnnotationConfigServletWebServerApplicationContext<strong i="6">@2b2948e2</strong>: startup date [Thu Jan 30 10:56:24 GMT 2020]; root of context hierarchy
2020-01-30 10:59:02.377 ERROR 1 --- [pool-4-thread-1] java.io.InputStreamReader                : Error while pumping stream.
java.io.EOFException: null
    at okio.RealBufferedSource.require(RealBufferedSource.java:61) ~[okio-1.15.0.jar!/:na]
    at okio.RealBufferedSource.readHexadecimalUnsignedLong(RealBufferedSource.java:303) ~[okio-1.15.0.jar!/:na]
    at okhttp3.internal.http1.Http1Codec$ChunkedSource.readChunkSize(Http1Codec.java:469) ~[okhttp-3.12.0.jar!/:na]
    at okhttp3.internal.http1.Http1Codec$ChunkedSource.read(Http1Codec.java:449) ~[okhttp-3.12.0.jar!/:na]
    at okio.RealBufferedSource$1.read(RealBufferedSource.java:439) ~[okio-1.15.0.jar!/:na]
    at java.io.InputStream.read(InputStream.java:101) ~[na:1.8.0_171]
    at io.fabric8.kubernetes.client.utils.BlockingInputStreamPumper.run(BlockingInputStreamPumper.java:49) ~[kubernetes-client-4.2.2.jar!/:na]
    at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) [na:1.8.0_171]
    at java.util.concurrent.FutureTask.run(FutureTask.java:266) [na:1.8.0_171]
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) [na:1.8.0_171]
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) [na:1.8.0_171]
    at java.lang.Thread.run(Thread.java:748) [na:1.8.0_171]
2020-01-30 10:59:02.394  INFO 1 --- [       Thread-2] o.s.j.e.a.AnnotationMBeanExporter        : Unregistering JMX-exposed beans on shutdown
2020-01-30 10:59:02.403  INFO 1 --- [       Thread-2] o.s.j.e.a.AnnotationMBeanExporter        : Unregistering JMX-exposed beans
2020-01-30 10:59:02.514  WARN 1 --- [       Thread-2] .s.c.a.CommonAnnotationBeanPostProcessor : Invocation of destroy method failed on bean with name 'proxyService': eu.openanalytics.containerproxy.ContainerProxyException: Failed to stop container
2020-01-30 10:59:02.525  INFO 1 --- [       Thread-2] io.undertow.servlet                      : Destroying Spring FrameworkServlet 'dispatcherServlet'

Ich habe eine Lösung für dieses Problem gefunden. Dies ist eigentlich kein Problem in Shinyproxy oder Containerproxy, da die Spring Boot-App korrekt und ordnungsgemäß heruntergefahren wird.

Das Problem ist der Beiwagencontainer kubctl proxy . Für Kubernetes ist nicht klar, dass Containerproxy auf den Sidecar-Container angewiesen ist, um mit Kubernetes selbst zu kommunizieren. Bei einer neuen Bereitstellung sendet Kubernetes also SIGTERM sowohl an den Proxy als auch an den Sidecar-Container in allen alten Pods. Der Sidecar-Container wird sofort beendet und containerproxy kann nicht mit Kubernetes kommunizieren.

Ich habe gelesen, dass Kubernetes im Begriff ist, diese Start- und Shutdown-Abhängigkeiten in v1.18 zu lösen, wie hier dokumentiert:
https://github.com/kubernetes/enhancements/issues/753
https://banzaicloud.com/blog/k8s-sidecars/

Bis dahin gibt es eine einfache Problemumgehung, um die folgende Lebenszyklusanmerkung in den Sidecar-Container einzufügen:

          lifecycle:
            preStop:
              exec:
                command: ["sh", "-c", "sleep 5"] # wait 5 seconds to let shinyproxy remove the pods on graceful shutdown

Ich kann bestätigen, dass der Fix von @fmannhardt dies behebt. Ich danke dir sehr!

Hallo alle

Bei neueren Versionen von ShinyProxy (ich bin mir nicht sicher, welche Version genau, aber mindestens ShinyProxy 2.3.1) muss kein Kube-Proxy-Sidecar verwendet werden. ShinyProxy erkennt automatisch den Standort und die Authentifizierung der Kubernetes-API.
Daher denke ich, dass dieses Problem automatisch gelöst wird.
Trotzdem vielen Dank für Ihre Zeit und Untersuchung!

War diese Seite hilfreich?
0 / 5 - 0 Bewertungen