0%
Instalação e configuração

Instalação

Um cluster local descartável e um kubectl apontando para o lugar certo.

15-20 min

Instalação e configuração

Aprender Kubernetes em um cluster de produção é uma má ideia por um motivo simples: você vai quebrar coisas, e é exatamente isso que precisa fazer. Você precisa de um cluster que possa ser destruído com um comando e recriado em dois minutos, no qual um erro não custa nada.

Existem duas maneiras de obter isso em uma estação de trabalho, e a escolha não é indiferente. O minikube simula um cluster completo em uma máquina virtual ou em um contêiner, com extensões prontas para uso — um painel de controle, um controlador de entrada, um simulador de balanceador de carga. O kind (Kubernetes in Docker) executa cada nó como um contêiner Docker: é mais leve, inicia mais rápido e é a escolha habitual em integração contínua.

Mas, antes do cluster, existe o kubectl. É o ponto que os iniciantes costumam inverter: o kubectl não é um componente do cluster, é um cliente HTTP que fala com uma API remota. Ele é instalado de forma independente, funciona com qualquer cluster e lê em um arquivo de configuração local com qual cluster deve falar. Metade dos “não funciona” dos primeiros dias vem daí: o kubectl consulta um cluster diferente daquele que você imagina.

Esta lição instala as ferramentas e depois se detém nesse arquivo de configuração — contextos e namespaces — porque é ele que vai evitar que, um dia, você aplique em produção um manifesto destinado à sua máquina.

Instalar o kubectl

O kubectl é um binário único, sem dependências. Escolha o método do seu sistema:

# macOS com Homebrew
brew install kubectl

# Linux (Debian/Ubuntu) : repositório oficial do Kubernetes
sudo apt-get update
sudo apt-get install -y apt-transport-https ca-certificates curl gnupg
curl -fsSL https://pkgs.k8s.io/core:/stable:/v1.31/deb/Release.key \
  | sudo gpg --dearmor -o /etc/apt/keyrings/kubernetes-apt-keyring.gpg
echo 'deb [signed-by=/etc/apt/keyrings/kubernetes-apt-keyring.gpg] https://pkgs.k8s.io/core:/stable:/v1.31/deb/ /' \
  | sudo tee /etc/apt/sources.list.d/kubernetes.list
sudo apt-get update && sudo apt-get install -y kubectl
# Windows com winget
winget install -e --id Kubernetes.kubectl

Em seguida, verifique a instalação. O comando a seguir exibe a versão do cliente e depois tenta alcançar um servidor:

kubectl version --client

Enquanto nenhum cluster estiver em execução, um comando como kubectl get nodes falhará com uma mensagem de conexão recusada. Isso é normal e já é uma informação útil: o cliente funciona, só não tem ninguém com quem conversar.

Qual versão escolher

O Kubernetes tolera uma diferença de uma versão menor entre o cliente e o servidor. Um kubectl 1.31 conversa corretamente com um cluster 1.30, 1.31 ou 1.32. Além disso, alguns recursos podem se tornar invisíveis para o cliente sem uma mensagem clara. Em caso de comportamento inexplicável, a primeira verificação é esta:

# Compara a versão do cliente e a do servidor
kubectl version

Opção A: minikube

O minikube inicia um cluster de um único nó em um driver de virtualização. O driver docker é o mais simples se o Docker já estiver instalado.

# Instalação (macOS)
brew install minikube

# Inicialização: a primeira execução baixa a imagem do nó, conte alguns minutos
minikube start --driver=docker --cpus=2 --memory=4096

# O minikube escreveu a configuração de conexão para o kubectl: vamos verificar
kubectl get nodes

Saída esperada:

NAME       STATUS   ROLES           AGE   VERSION
minikube   Ready    control-plane   47s   v1.31.0

Um único nó, que abriga ao mesmo tempo o plano de controle e as suas cargas de trabalho. Em produção, esses papéis são separados; aqui, a simplificação não tem consequência para o aprendizado.

Os comandos de gerenciamento do ciclo de vida:

minikube status          # estado do cluster e de seus componentes
minikube stop            # para sem destruir: o estado é preservado
minikube start           # reinicia de onde havia parado
minikube delete          # destrói tudo, inclusive os dados
minikube dashboard       # abre a interface web no navegador

O minikube oferece extensões que podem ser ativadas. Duas são úteis para o restante do curso:

# O controlador de entrada, necessário para os Ingress da lição 6
minikube addons enable ingress

# O servidor de métricas, necessário para kubectl top e o autoscaling
minikube addons enable metrics-server

minikube addons list     # ver tudo o que está disponível

Opção B: kind

O kind transforma cada nó em um contêiner Docker. Inicialização mais rápida, consumo menor e, sobretudo, a possibilidade de simular vários nós — útil para observar o reagendamento de um Pod.

# Instalação (macOS)
brew install kind

# Cluster de um nó
kind create cluster --name atelier

# Verificação
kubectl cluster-info --context kind-atelier

Para um cluster com vários nós, o kind lê um arquivo de configuração. Atenção: esse arquivo usa a API do kind, não a do Kubernetes, daí um apiVersion de aparência incomum.

# kind-cluster.yaml
kind: Cluster
apiVersion: kind.x-k8s.io/v1alpha4
name: atelier
nodes:
  - role: control-plane
  - role: worker
  - role: worker
kind create cluster --config kind-cluster.yaml

kubectl get nodes
# atelier-control-plane, atelier-worker, atelier-worker2

kind delete cluster --name atelier   # remoção

Uma diferença que convém conhecer desde já: o kind não enxerga as imagens do seu daemon Docker local. Uma imagem construída localmente precisa ser carregada explicitamente no cluster; caso contrário, o Pod fica travado em ErrImagePull, embora docker images mostre a imagem presente.

docker build -t mon-api:dev .
kind load docker-image mon-api:dev --name atelier

Com o minikube, o equivalente consiste em apontar o cliente Docker para o daemon interno do cluster:

eval $(minikube docker-env)
docker build -t mon-api:dev .   # a imagem é construída dentro do cluster

Nos dois casos, especifique imagePullPolicy: IfNotPresent nos seus manifestos; caso contrário, o Kubernetes tentará baixar a imagem dev de um registro público onde ela não existe.

O arquivo kubeconfig e os contextos

Esse arquivo é a peça que se ignora por tempo demais. Por padrão em ~/.kube/config, ele contém três listas independentes:

  • clusters: os endereços dos servidores de API e seus certificados;
  • users: as identidades usadas para autenticação;
  • contexts: as associações (cluster, usuário, namespace).

Um contexto é, portanto, simplesmente a tripla que o kubectl usa a cada chamada. Mudar de contexto é mudar o cluster de destino — daí a necessidade de saber sempre qual deles está ativo.

# Listar os contextos; o asterisco marca o que está ativo
kubectl config get-contexts

# Exibir somente o nome do contexto ativo
kubectl config current-context

# Alternar de cluster
kubectl config use-context kind-atelier

# Ver a configuração completa, com segredos ocultos
kubectl config view

Adquira o hábito de verificar o contexto antes de qualquer comando de escrita. É um reflexo que parece exagerado até o dia em que evita um kubectl delete no cluster errado:

# Tornar o contexto visível no prompt, ou ao menos verificá-lo
kubectl config current-context && kubectl get nodes

Os namespaces

Um namespace é uma partição lógica do cluster. Ele permite isolar conjuntos de recursos por equipe, por ambiente ou por aplicação, e serve de base para cotas e regras de acesso.

Um ponto importante que costuma surpreender: o namespace não isola a rede. Por padrão, um Pod do namespace dev pode alcançar um Pod do namespace prod. Esse tipo de isolamento exige NetworkPolicy, que depende do plugin de rede instalado.

# Os namespaces criados por padrão
kubectl get namespaces
# default, kube-system, kube-public, kube-node-lease

O kube-system abriga os componentes do cluster. Não se implanta nada pessoal nele, e evita-se aplicar um manifesto ali por descuido — mais um motivo para ficar de olho no contexto.

Crie um namespace de trabalho, de preferência de forma declarativa, para que sua definição fique no seu repositório:

apiVersion: v1
kind: Namespace
metadata:
  name: atelier
  labels:
    environnement: developpement
kubectl apply -f namespace.yaml

# Equivalente imperativo, prático para algo descartável
kubectl create namespace atelier

Todos os comandos de leitura e escrita aceitam -n (ou --namespace). Sem essa opção, o kubectl usa o namespace registrado no contexto ativo, na maioria das vezes default:

kubectl get pods -n atelier          # em um namespace específico
kubectl get pods --all-namespaces    # em todos; alias: -A

# Alterar o namespace padrão do contexto ativo
kubectl config set-context --current --namespace=atelier

Este último comando evita repetir -n atelier cinquenta vezes. Ele tem um preço: você deixa de ver, no comando, onde ele se aplica. Verifique, portanto, com regularidade:

kubectl config view --minify --output 'jsonpath={..namespace}'

Por fim, uma propriedade que é melhor conhecer antes de aprendê-la na prática: excluir um namespace exclui tudo o que ele contém, em cascata e sem confirmação.

kubectl delete namespace atelier   # Pods, Services, Secrets, PVC: tudo vai embora

Verificar se tudo está no lugar

Execute estes quatro comandos em sequência. Se todos responderem, seu ambiente está pronto para a próxima lição:

# 1. O cliente alcança o servidor de API
kubectl cluster-info

# 2. O(s) nó(s) estão Ready
kubectl get nodes

# 3. Os componentes do plano de controle estão em execução
kubectl get pods -n kube-system

# 4. Um Pod efêmero consegue realmente iniciar e acessar a rede externa
kubectl run test --image=busybox:1.36 --rm -it --restart=Never -- \
  wget -qO- https://kubernetes.io/fr/ | head -n 5

O quarto merece uma explicação: --rm remove o Pod ao sair, --restart=Never cria um Pod isolado em vez de um Deployment, e -it conecta o terminal. Se ele funcionar, o runtime baixa imagens, o escalonador posiciona os Pods e a rede de saída funciona. Três validações em um único comando.

Autocompletar e aliases

Os nomes de recursos gerados pelo Kubernetes são longos e aleatórios (mon-api-7d4b8c9f5-xk2mp). Sem autocompletar, você vai redigitá-los à mão o dia inteiro.

# bash : adicionar ao ~/.bashrc
source <(kubectl completion bash)
alias k=kubectl
complete -o default -F __start_kubectl k

# zsh : adicionar ao ~/.zshrc
source <(kubectl completion zsh)
alias k=kubectl
# PowerShell : adicionar ao perfil ($PROFILE)
kubectl completion powershell | Out-String | Invoke-Expression
Set-Alias -Name k -Value kubectl

Duas opções de leitura que vale conhecer desde já, porque são usadas o tempo todo:

# -o wide adiciona o IP do Pod e o nó que o hospeda
kubectl get pods -o wide

# -w (watch) acompanha as mudanças em tempo real: indispensável durante um deployment
kubectl get pods -w

Pontos principais

  • O kubectl é um cliente independente do cluster. Ele obedece ao contexto ativo de ~/.kube/config, e o erro mais frequente do iniciante é falar com um cluster diferente daquele que imagina.
  • O minikube oferece um cluster completo com extensões (ingress, metrics-server); o kind é mais leve e permite simular vários nós. Ambos servem para este curso.
  • Uma imagem construída localmente não é visível para o cluster: use kind load docker-image ou eval $(minikube docker-env) e declare imagePullPolicy: IfNotPresent.
  • Um namespace particiona os recursos e serve de base para cotas, mas não isola a rede sem NetworkPolicy. Excluí-lo destrói todo o seu conteúdo em cascata.
  • Sempre verifique um deployment pelo estado observado (kubectl get, kubectl describe) e confira o contexto ativo antes de qualquer comando de escrita.

Dica: destrua e recrie seu cluster local pelo menos uma vez. Saber que é possível recomeçar do zero em dois minutos muda completamente a relação com a experimentação.

Comentários

Os comentários são alimentados pelo GitHub Discussions

Conecte-se com o GitHub para participar da discussão

Link copiado!