Configurar a separação de cargas de trabalho no GKE


Nesta página, mostramos como instruir o Google Kubernetes Engine (GKE) a programar os pods juntos, separadamente ou em locais específicos.

A separação de cargas de trabalho permite usar taints e tolerâncias para instruir o GKE a separar pods em nós diferentes e colocar pods em nós que atendam a critérios específicos ou programar cargas de trabalho específicas juntas. O que você precisa fazer para configurar a separação da carga de trabalho depende da configuração do cluster do GKE. A tabela a seguir descreve as diferenças:

Configuração da separação de cargas de trabalho

Adicione uma tolerância para um par de chave-valor único à especificação do pod e selecione esse par usando um nodeSelector. O GKE cria nós, aplica o taint de nó correspondente e programa o pod no nó.

Para instruções, consulte Cargas de trabalho separadas em clusters do Autopilot nesta página.

Padrão sem provisionamento automático de nós
  1. Criar um pool de nós com um taint e um rótulo de nó
  2. Adicionar uma tolerância a esse taint à especificação do pod

Para instruções, consulte Isolar suas cargas de trabalho em pools de nós dedicados.

Este guia usa um cenário de exemplo em que você tem duas cargas de trabalho, um job em lote e um servidor da Web que você quer separar.

Quando usar a separação de cargas de trabalho no GKE

A separação de carga de trabalho é útil quando você tem cargas de trabalho que desempenham papéis diferentes e não podem ser executadas nas mesmas máquinas. Alguns cenários de exemplo:

  • Você tem uma carga de trabalho de coordenador em lote que cria os jobs que você quer manter separados.
  • Você executa um servidor de jogos com uma carga de trabalho de combinação que você quer separar dos pods de sessão.
  • Você quer separar partes da sua pilha umas das outras, como separar um servidor de um banco de dados.
  • Você quer separar algumas cargas de trabalho por motivos de conformidade ou política.

Preços

Nos clusters do Autopilot, você é cobrado pelos recursos que seus pods solicitam durante a execução. Para mais detalhes, consulte Preços do Autopilot. Os pods que usam a separação de cargas de trabalho têm solicitações mínimas de recursos mais altas aplicadas do que os pods comuns.

Nos clusters padrão, a cobrança é feita com base na configuração de hardware e no tamanho de cada nó, independentemente de os pods estarem em execução neles. Para mais detalhes, consulte Preços do Standard.

Antes de começar

Antes de começar, verifique se você realizou as tarefas a seguir:

  • Ativar a API Google Kubernetes Engine.
  • Ativar a API Google Kubernetes Engine
  • Se você quiser usar a Google Cloud CLI para essa tarefa, instale e, em seguida, inicialize a CLI gcloud. Se você instalou a CLI gcloud anteriormente, instale a versão mais recente executando gcloud components update.

Cargas de trabalho separadas em clusters do Autopilot

Para separar as cargas de trabalho uma da outra, adicione uma tolerância e um seletor de nó a cada especificação de carga de trabalho que define o nó em que a carga de trabalho será executada. Esse método também funciona em clusters padrão que têm o provisionamento automático de nós ativado.

  1. Salve o seguinte manifesto como web-server.yaml:

    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: web-server
    spec:
      replicas: 6
      selector:
        matchLabels:
          pod: nginx-pod
      template:
        metadata:
          labels:
            pod: nginx-pod
        spec:
          tolerations:
          - key: group
            operator: Equal
            value: "servers"
            effect: NoSchedule
          nodeSelector:
            group: "servers"
          containers:
          - name: web-server
            image: nginx
    

    Esse manifesto inclui os seguintes campos:

    • spec.tolerations: o GKE pode colocar os pods em nós que tenham o taint group=servers:NoSchedule. O GKE não pode programar pods que não tenham essa tolerância nesses nós.
    • spec.nodeSelector: o GKE precisa colocar os pods em nós que tenham o rótulo de nó group: servers.

    O GKE adiciona os rótulos e taints correspondentes aos nós que ele provisiona automaticamente para executar esses pods.

  2. Salve o seguinte manifesto como batch-job.yaml:

    apiVersion: batch/v1
    kind: Job
    metadata:
      name: batch-job
    spec:
      completions: 5
      backoffLimit: 3
      ttlSecondsAfterFinished: 120
      template:
        metadata:
          labels:
            pod: pi-pod
        spec:
          restartPolicy: Never
          tolerations:
          - key: group
            operator: Equal
            value: "jobs"
            effect: NoSchedule
          nodeSelector:
            group: "jobs"
          containers:
          - name: pi
            image: perl
            command: ["perl",  "-Mbignum=bpi", "-wle", "print bpi(2000)"]
    

    Esse manifesto inclui os seguintes campos:

    • spec.tolerations: o GKE pode colocar os pods em nós que tenham o taint group=jobs:NoSchedule. O GKE não pode programar pods que não tenham essa tolerância nesses nós.
    • spec.nodeSelector: o GKE precisa colocar os pods em nós que tenham o rótulo de nó group: jobs.

    O GKE adiciona os rótulos e taints correspondentes aos nós que ele provisiona automaticamente para executar esses pods.

  3. Implante as cargas de trabalho:

    kubectl apply -f batch-job.yaml web-server.yaml
    

Quando você implanta as cargas de trabalho, o GKE faz o seguinte para cada uma delas:

  1. O GKE procura nós que têm o taint e o rótulo de nó correspondentes especificados no manifesto. Se houver nós e tiver recursos disponíveis, o GKE programa a carga de trabalho no nó.
  2. Se o GKE não encontrar um nó atual qualificado para programar a carga de trabalho, ele criará um novo nó e aplicará o taint de nó e o rótulo de nó correspondentes com base no manifesto. O GKE coloca o pod no novo nó.

A presença do efeito NoSchedule no taint do nó garante que as cargas de trabalho sem uma tolerância não sejam colocadas no nó.

Verificar a separação da carga de trabalho

Liste seus pods para encontrar os nomes dos nós:

kubectl get pods --output=wide

O resultado será assim:

NAME                          READY   ...   NODE
batch-job-28j9h               0/1     ...   gk3-sandbox-autopilot-nap-1hzelof0-ed737889-2m59
batch-job-78rcn               0/1     ...   gk3-sandbox-autopilot-nap-1hzelof0-ed737889-2m59
batch-job-gg4x2               0/1     ...   gk3-sandbox-autopilot-nap-1hzelof0-ed737889-2m59
batch-job-qgsxh               0/1     ...   gk3-sandbox-autopilot-nap-1hzelof0-ed737889-2m59
batch-job-v4ksf               0/1     ...   gk3-sandbox-autopilot-nap-1hzelof0-ed737889-2m59
web-server-6bb8cd79b5-dw4ds   1/1     ...   gk3-sandbox-autopilot-nap-1eurxgsq-f2f3c272-n6xm
web-server-6bb8cd79b5-g5ld6   1/1     ...   gk3-sandbox-autopilot-nap-1eurxgsq-9f447e18-275z
web-server-6bb8cd79b5-jcdx5   1/1     ...   gk3-sandbox-autopilot-nap-1eurxgsq-9f447e18-275z
web-server-6bb8cd79b5-pxdzw   1/1     ...   gk3-sandbox-autopilot-nap-1eurxgsq-ccd22fd9-qtfq
web-server-6bb8cd79b5-s66rw   1/1     ...   gk3-sandbox-autopilot-nap-1eurxgsq-ccd22fd9-qtfq
web-server-6bb8cd79b5-zq8hh   1/1     ...   gk3-sandbox-autopilot-nap-1eurxgsq-f2f3c272-n6xm

Esta saída mostra que os pods batch-job e web-server sempre são executados em nós diferentes.

Limitações da separação de cargas de trabalho com taints e tolerâncias

Não é possível usar os seguintes prefixos de chave para separação de cargas de trabalho:

  • Chaves específicas do GKE e do Kubernetes
  • *cloud.google.com/
  • *kubelet.kubernetes.io/
  • *node.kubernetes.io/

Use suas próprias chaves exclusivas para fazer a separação das cargas de trabalho.

Cargas de trabalho separadas em clusters padrão sem provisionamento automático de nós

Para separar cargas de trabalho em clusters padrão sem provisionamento automático de nós, é necessário criar manualmente pools de nós com os taints e rótulos de nós adequados para acomodar suas cargas de trabalho. Para instruções, consulte Isolar suas cargas de trabalho em pools de nós dedicados. Use essa abordagem apenas se você tiver requisitos específicos que exigem o gerenciamento manual dos pools de nós.

Criar um cluster com taints de nó

Quando você cria um cluster no GKE, é possível atribuir taints de nó a ele. Isso atribui os taints a todos os nós criados com o cluster.

Se você criar um pool de nós, ele não herdará os taints do cluster. Se quiser ter taints no pool de nós, use a flag --node-taints ao criar o pool de nós.

Se você criar um cluster Standard com taints de nós que têm o efeito NoSchedule ou NoExecute, o GKE não poderá programar alguns componentes gerenciados por ele, como kube-dns ou metrics-server, no pool de nós padrão que o GKE cria quando você cria o cluster. O GKE não pode programar esses componentes porque eles não têm as tolerâncias correspondentes para os taints de nós. Você precisa adicionar um novo pool de nós que atende a uma destas condições:

  • Sem taints
  • Um taint com o efeito PreferNoSchedule
  • O taint components.gke.io/gke-managed-components=true:NoSchedule

Qualquer uma dessas condições permite que o GKE programe componentes gerenciados pelo GKE no novo pool de nós.

Para instruções, consulte Isolar cargas de trabalho em nós dedicados.

gcloud

Crie um cluster com taints de nó:

gcloud container clusters create CLUSTER_NAME \
    --node-taints KEY=VALUE:EFFECT

Substitua:

  • CLUSTER_NAME: o nome do novo cluster;
  • EFFECT: um dos seguintes efeitos: PreferNoSchedule, NoSchedule ou NoExecute.
  • KEY=VALUE: um par de chave-valor associado ao EFFECT.

Console

Crie um cluster com taints de nó:

  1. Acesse a página Google Kubernetes Engine no console do Google Cloud.

    Acessar o Google Kubernetes Engine

  2. Clique em Criar.

  3. Configure o cluster como quiser.

  4. No painel de navegação, em Pools de nós, expanda o pool de nós que você quer modificar e clique em Metadados.

  5. Na seção Taints de nó, clique em Adicionar taint.

  6. Na lista suspensa Efeito, selecione o efeito pretendido.

  7. Insira o par de chave-valor pretendido nos campos Chave e Valor.

  8. Clique em Criar.

API

Quando você usar a API para criar um cluster, inclua o campo nodeTaints em `nodeConfig:

POST https://container.googleapis.com/v1/projects/PROJECT_ID/zones/COMPUTE_ZONE/clusters

{
  'cluster': {
    'name': 'example-cluster',
    'nodeConfig': {
      'nodeTaints': [
        {
          'key': 'special',
          'Value': 'gpu',
          'effect': 'PreferNoSchedule'
        }
      ]
      ...
    }
    ...
  }
}

Remover todos os taints de um pool de nós

Para remover todos os taints de um pool de nós, execute o comando a seguir:

gcloud beta container node-pools update POOL_NAME \
    --node-taints="" \
    --cluster=CLUSTER_NAME

Substitua:

  • POOL_NAME: o nome do pool de nós que será alterado.
  • CLUSTER_NAME: o nome do cluster do pool de nós.

A seguir