Todos os produtos
Search
Central de documentação

Container Service for Kubernetes:Achieve zero-downtime rolling updates with graceful shutdown

Última atualização: Oct 15, 2026

Configure as sondas de prontidão, os readinessGates, os hooks preStop e o esvaziamento de conexões do Server Load Balancer (SLB) para garantir atualizações graduais sem tempo de inatividade no ACK.

Como funciona

A estratégia de atualização gradual (RollingUpdate) para Deployments substitui os Pods um a um para garantir a disponibilidade contínua. O processo possui três fases:

  1. Fase de inicialização: O Kubernetes cria um novo Pod (v2) e aguarda a aprovação na sonda de prontidão antes de rotear qualquer tráfego do service para ele.

  2. Fase de deslocamento de tráfego: Com os readinessGates ativados, o novo Pod precisa passar na verificação de prontidão. Em seguida, o sistema registra o IP dele nos Endpoints do service e no grupo de servidores de backend do SLB, encerra o Pod antigo (v1) e remove o IP dele dos Endpoints.

    Consulte How readinessGates works .
  3. Fase de desligamento graceful: Antes da exclusão, o Pod antigo executa seu hook preStop e usa o terminationGracePeriodSeconds para concluir o processamento das conexões, enquanto o SLB esvazia as requisições em andamento. Isso garante a conclusão de todas as requisições, resultando em uma atualização sem tempo de inatividade.

image

Pré-requisitos

Implante um aplicativo de exemplo

Este exemplo implanta um aplicativo NGINX sem estado (stateless).

Console

  1. Na página ACK Clusters, clique no nome do seu cluster. No painel de navegação à esquerda, clique em Workloads > Deployments.

  2. Na página Deployments, clique em Create from YAML. Cole o YAML a seguir e clique em Create.

    Sample application YAML

    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: nginx-deployment-demo
    spec:
      replicas: 1                 # Set to 2 or more for production HA. Set to 1 for demonstration purposes.
      selector:
        matchLabels:
          app: nginx-demo
      # Rolling update strategy: ensures service availability during updates.
      # strategy:
        # type: RollingUpdate     # Default strategy for Deployments.
        # rollingUpdate:
          # maxUnavailable: "25%" # Default. Max 25% of Pods can be unavailable during the update.
          # maxSurge: "25%"       # Default. Max 25% extra Pods can be created above the desired replica count.
      template:
        metadata:
          labels:
            app: nginx-demo 
        spec:
          # Pod-level graceful shutdown limit. Must be greater than the sum of preStop execution and app cleanup time.
          terminationGracePeriodSeconds: 60 
          readinessGates:
          - conditionType: service.readiness.alibabacloud.com/nginx-demo-service # Set the Readiness Gate for the nginx-demo-service Service.
          containers:
          - name: nginx
            image: anolis-registry.cn-zhangjiakou.cr.aliyuncs.com/openanolis/nginx:1.14.1-8.6
            ports:
            - containerPort: 80
            resources:
              requests:
                cpu: 500m
                memory: 1Gi
              limits:
                cpu: 500m
            # --- Health check probes ---
            # startup probe: Ensures the application in the container has started.
            startupProbe:
              httpGet:
                path: / # Accessing the default NGINX root path indicates a successful startup.
                port: 80
              # Allow sufficient time for startup. Total timeout = failureThreshold * periodSeconds.
              # Here: 30 * 10 = 300 seconds.
              failureThreshold: 30
              periodSeconds: 10
            # readiness probe: Determines whether the container is ready to receive traffic.
            readinessProbe:
              httpGet:
                path: /
                port: 80
              initialDelaySeconds: 5  # Probing starts 5 seconds after the container starts.
              periodSeconds: 5        # Probe every 5 seconds.
              timeoutSeconds: 2       # Probe timeout duration.
              successThreshold: 1     # 1 success marks the Pod as ready.
              failureThreshold: 3     # 3 consecutive failures mark the Pod as not ready.
            # --- Pod graceful shutdown configuration ---
            lifecycle:
              preStop:
                exec:
                  # For reliable graceful shutdown, define a custom hook that handles in-flight requests based on your application logic.
                  # Using sleep alone is not recommended as it does not guarantee a clean exit.
                  command: ["sh", "-c", "sleep 30 && /usr/sbin/nginx -s quit"]
    ---           
    apiVersion: v1
    kind: Service
    metadata:
      name: nginx-demo-service
      annotations:
        # Timeout for connection draining. This value should align with the application's preStop logic. Range: 10-900.
        service.beta.kubernetes.io/alibaba-cloud-loadbalancer-connection-drain-timeout: "30" 
        # Enable connection draining.
        service.beta.kubernetes.io/alibaba-cloud-loadbalancer-connection-drain: "on"
    spec:
      type: LoadBalancer
      selector:
        app: nginx-demo 
      ports:
        - protocol: TCP
          port: 80
  3. Na janela pop-up, localize o aplicativo, clique em View e verifique se o status do Pod é Running.

kubectl

  1. Obtain the kubeconfig file of a cluster and use kubectl to connect to the cluster.

  2. Salve o YAML a seguir como nginx-demo.yaml.

    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: nginx-deployment-demo
    spec:
      replicas: 1                 # Set to 2 or more for production HA. Set to 1 for demonstration purposes.
      selector:
        matchLabels:
          app: nginx-demo
      # Rolling update strategy: ensures service availability during updates.
      # strategy:
        # type: RollingUpdate     # Default strategy for Deployments.
        # rollingUpdate:
          # maxUnavailable: "25%" # Default. Max 25% of Pods can be unavailable during the update.
          # maxSurge: "25%"       # Default. Max 25% extra Pods can be created above the desired replica count.
      template:
        metadata:
          labels:
            app: nginx-demo 
        spec:
          # Pod-level graceful shutdown limit. Must be greater than the sum of preStop execution and app cleanup time.
          terminationGracePeriodSeconds: 60 
          readinessGates:
          - conditionType: service.readiness.alibabacloud.com/nginx-demo-service # Set the Readiness Gate for the nginx-demo-service Service.
          containers:
          - name: nginx
            image: anolis-registry.cn-zhangjiakou.cr.aliyuncs.com/openanolis/nginx:1.14.1-8.6
            ports:
            - containerPort: 80
            resources:
              requests:
                cpu: 500m
                memory: 1Gi
              limits:
                cpu: 500m
            # --- Health check probes ---
            # startup probe: Ensures the application in the container has started.
            startupProbe:
              httpGet:
                path: / # Accessing the default NGINX root path indicates a successful startup.
                port: 80
              # Allow sufficient time for startup. Total timeout = failureThreshold * periodSeconds.
              # Here: 30 * 10 = 300 seconds.
              failureThreshold: 30
              periodSeconds: 10
            # readiness probe: Determines whether the container is ready to receive traffic.
            readinessProbe:
              httpGet:
                path: /
                port: 80
              initialDelaySeconds: 5  # Probing starts 5 seconds after the container starts.
              periodSeconds: 5        # Probe every 5 seconds.
              timeoutSeconds: 2       # Probe timeout duration.
              successThreshold: 1     # 1 success marks the Pod as ready.
              failureThreshold: 3     # 3 consecutive failures mark the Pod as not ready.
            # --- Pod graceful shutdown configuration ---
            lifecycle:
              preStop:
                exec:
                  # For reliable graceful shutdown, define a custom hook that handles in-flight requests based on your application logic.
                  # Using sleep alone is not recommended as it does not guarantee a clean exit.
                  command: ["sh", "-c", "sleep 30 && /usr/sbin/nginx -s quit"]
    ---           
    apiVersion: v1
    kind: Service
    metadata:
      name: nginx-demo-service
      annotations:
        # Timeout for connection draining. This value should align with the application's preStop logic. Range: 10-900.
        service.beta.kubernetes.io/alibaba-cloud-loadbalancer-connection-drain-timeout: "30" 
        # Enable connection draining.
        service.beta.kubernetes.io/alibaba-cloud-loadbalancer-connection-drain: "on"
    spec:
      type: LoadBalancer
      selector:
        app: nginx-demo 
      ports:
        - protocol: TCP
          port: 80
  3. Implante o aplicativo NGINX e crie o service.

    kubectl apply -f nginx-demo.yaml
  4. Verifique se o Pod está Running.

    kubectl get pod | grep nginx-deployment-demo
  • Verificações de prontidão do Pod

    • startupProbe (sonda de inicialização): Verifica se aplicativos de inicialização lenta, como aplicativos Java, iniciaram. Até que seja bem-sucedida, o sistema pausa as sondas de prontidão e de atividade (liveness) para evitar reinicializações prematuras do contêiner.

    • readinessProbe (sonda de prontidão): Determina se um contêiner pode processar requisições. Em caso de sucesso, o Kubernetes adiciona o IP do Pod aos Endpoints do service, ativando o tráfego.

    • readinessGates: O Pod só fica pronto após a aprovação tanto do readinessProbe quanto dos readinessGates.

  • Desligamento graceful

    • Desligamento graceful do aplicativo

      • preStop: Hook executado antes do encerramento do contêiner. Configure-o para esvaziar as requisições em andamento e garantir um desligamento sem interrupções.

        Use um hook personalizado. O uso isolado do sleep pode não encerrar o processo corretamente.
      • terminationGracePeriodSeconds: Tempo máximo desde o encerramento do Pod até o SIGKILL. Padrão: 30 segundos. Deve exceder o tempo combinado do hook preStop e da limpeza do aplicativo.

    • Esvaziamento de conexões do SLB

      • Anotação service.beta.kubernetes.io/alibaba-cloud-loadbalancer-connection-drain: Ative o esvaziamento de conexões do SLB.

      • service.beta.kubernetes.io/alibaba-cloud-loadbalancer-connection-drain-timeout: Tempo limite do esvaziamento de conexões em segundos. Defina este valor próximo ao tempo de processamento do hook preStop.

    • Estratégia de atualização gradual (rolling update)

      • strategy: A estratégia padrão do Deployment é a RollingUpdate. Cria novos Pods gradualmente e remove os antigos após a prontidão dos novos para garantir a disponibilidade do service.

      • maxUnavailable: Número máximo de Pods indisponíveis durante uma atualização gradual. Padrão: 25%. Também aceita um número absoluto.

      • maxSurge: Número máximo de Pods extras acima da contagem de réplicas desejada durante uma atualização gradual. Valores mais altos aceleram as atualizações, mas consomem mais recursos. Padrão: 25%. Também aceita um número absoluto.

    Verifique a atualização gradual sem tempo de inatividade

    1. Obtain the kubeconfig file of a cluster and use kubectl to connect to the cluster.

    2. Obtenha a url do aplicativo de exemplo.

      export NGINX_ENDPOINT=$(kubectl get service nginx-demo-service -o jsonpath='{.status.loadBalancer.ingress[0].ip}{":"}{.spec.ports[0].port}')
      echo $NGINX_ENDPOINT
    3. Instale o hey. Execute um teste de carga com 200 conexões simultâneas e um total de 50.000 requisições. Uma única réplica conclui o teste em cerca de um minuto.

      hey -c 200 -n 50000  -disable-keepalive http://$NGINX_ENDPOINT

      Durante a execução do teste, abra um novo terminal e reinicie o Deployment imediatamente.

      kubectl rollout restart deployment nginx-deployment-demo
    4. Saídas esperadas:

      Cenário de implantação

      Saída esperada

      Sem a configuração de tempo de inatividade zero

      YAML de exemplo sem a configuração de tempo de inatividade zero

      apiVersion: apps/v1
      kind: Deployment
      metadata:
        name: nginx-deployment-demo
      spec:
        replicas: 1                 # Set to 2 or more for production HA. Set to 1 for demonstration purposes.
        selector:
          matchLabels:
            app: nginx-demo
        template:
          metadata:
            labels:
              app: nginx-demo 
          spec:
            containers:
            - name: nginx
              image: anolis-registry.cn-zhangjiakou.cr.aliyuncs.com/openanolis/nginx:1.14.1-8.6
              ports:
              - containerPort: 80
              resources:
                requests:
                  cpu: 500m
                  memory: 1Gi
                limits:
                  cpu: 500m
      ---           
      apiVersion: v1
      kind: Service
      metadata:
        name: nginx-demo-service
      spec:
        type: LoadBalancer
        selector:
          app: nginx-demo 
        ports:
          - protocol: TCP
            port: 80

      Ocorre perda de tráfego.

      Status code distribution:
        [200]	49644 responses
      
      Error distribution:
        [320]	Get "http://114.215.XXX.XXX": dial tcp 114.215.XXX.XXX:80: connect: connection refused
        [18]	Get "http://114.215.XXX.XXX": dial tcp 114.215.XXX.XXX:80: connect: no route to host
        [18]	Get "http://114.215.XXX.XXX": dial tcp 114.215.XXX.XXX:80: connect: operation timed out

      Com a configuração de tempo de inatividade zero

      Não há perda de tráfego.

      Status code distribution:
        [200]	50000 responses

    Perguntas frequentes

    Status do Pod: Running, mas não pronto

    Causa: Geralmente, ocorre devido a uma falha na sonda de inicialização ou de prontidão.

    Solução:

    • Configure a sonda de prontidão: Na página Edit dos Workloads de destino, verifique se o caminho da verificação de integridade (por exemplo, /healthz) e a porta correspondem ao aplicativo. Para aplicativos de inicialização lenta, aumente o Unhealthy Threshold para evitar falhas prematuras.

      Desative temporariamente a verificação de Readiness , acesse o terminal do Pod e use um comando como curl e verifique se a verificação de integridade responde corretamente.
    • Solução de problemas do aplicativo: Verifique os Events e Logs do Pod. Selecione Show the log of the last container exit.

    Referências