Helm Charts: Gerenciamento de Pacotes do Kubernetes
Implantações do Kubernetes com gerenciamento de pacotes Helm
Helm revolucionou a implantação de aplicações no Kubernetes ao introduzir conceitos de gerenciamento de pacotes familiares aos sistemas operacionais tradicionais.
Com o crescimento da adoção do Kubernetes, gerenciar aplicações complexas com dezenas de arquivos YAML torna-se desafiador. Os Helm Charts resolvem esse problema ao agrupar todos os recursos em pacotes versionados e configuráveis.
Esta bela imagem foi gerada pelo modelo de IA Flux 1 dev.
Compreendendo o Helm: O Gerenciador de Pacotes do Kubernetes
O Helm é para o Kubernetes o que o apt é para o Debian, o yum para o RedHat, ou o Homebrew para o macOS. Ele empacota aplicações Kubernetes em Charts – coleções de arquivos que descrevem recursos Kubernetes relacionados. Um único Chart pode implantar uma pilha de aplicação completa: servidores web, bancos de dados, camadas de cache, regras de ingresso e componentes de monitoramento. Para aqueles novos no Kubernetes, uma Lista de Comandos do Kubernetes fornece comandos e conceitos essenciais para começar.
Por que o Helm Importa no DevOps Moderno
Redução de Complexidade: Em vez de gerenciar 20+ arquivos YAML, você gerencia um único Chart com valores personalizáveis.
Reprodutibilidade: Implante configurações idênticas em desenvolvimento, homologação e produção com sobrescritas de valores específicas do ambiente. Isso é especialmente valioso ao implantar arquiteturas de microsserviços complexas onde a consistência importa.
Controle de Versão: Os Charts são versionados, permitindo rollback e rastreamento de upgrades fáceis.
Ecossistema da Comunidade: Milhares de Charts pré-construídos disponíveis através do Artifact Hub (anteriormente Helm Hub) para aplicações populares como PostgreSQL, Redis, NGINX, Prometheus e muito mais.
Poder de Templating: Go templates permitem a geração dinâmica de recursos com base em valores de entrada, reduzindo a duplicação.
Arquitetura e Conceitos Centrais do Helm
Arquitetura do Helm 3
O Helm 3 simplificou a arquitetura removendo o Tiller, o componente problemático de servidor do Helm 2:
- Cliente Helm: Ferramenta de linha de comando que interage diretamente com a API do Kubernetes
- Chart: Formato de pacote contendo templates e metadados
- Release: Uma instância de um Chart executando em um cluster Kubernetes
- Repositório: Local de armazenamento para Charts (servidor HTTP ou registro OCI)
Componentes Chave de um Helm Chart
my-app-chart/
├── Chart.yaml # Metadados e versão do Chart
├── values.yaml # Valores de configuração padrão
├── charts/ # Charts dependentes
├── templates/ # Templates de recursos Kubernetes
│ ├── deployment.yaml
│ ├── service.yaml
│ ├── ingress.yaml
│ ├── _helpers.tpl # Helpers de template
│ └── NOTES.txt # Notas pós-instalação
├── .helmignore # Arquivos a ignorar ao empacotar
├── README.md
└── LICENSE
Criando seu Primeiro Helm Chart
Inicializar um Novo Chart
helm create my-application
cd my-application
Isso gera um Chart inicial com templates de exemplo para deployment, service e ingress.
Chart.yaml: Definindo Metadados
apiVersion: v2
name: my-application
description: Um chart de aplicação pronto para produção
type: application
version: 1.0.0 # Versão do Chart
appVersion: "2.4.1" # Versão da aplicação
maintainers:
- name: Your Team
email: team@company.com
dependencies:
- name: postgresql
version: "12.x.x"
repository: "https://charts.bitnami.com/bitnami"
condition: postgresql.enabled
Values.yaml: Gerenciamento de Configuração
O arquivo values.yaml define configurações padrão que os usuários podem sobrescrever. Esta abordagem separa a configuração dos templates, facilitando o gerenciamento de diferentes ambientes (desenvolvimento, homologação, produção) e a personalização de implantações sem modificar os arquivos de template.
replicaCount: 3
image:
repository: myapp/backend
tag: "1.0.0"
pullPolicy: IfNotPresent
service:
type: ClusterIP
port: 80
ingress:
enabled: true
className: "nginx"
annotations:
cert-manager.io/cluster-issuer: "letsencrypt-prod"
hosts:
- host: myapp.example.com
paths:
- path: /
pathType: Prefix
resources:
limits:
cpu: 500m
memory: 512Mi
requests:
cpu: 250m
memory: 256Mi
autoscaling:
enabled: true
minReplicas: 3
maxReplicas: 10
targetCPUUtilizationPercentage: 80
Templates: Manifestos Kubernetes Dinâmicos
Os templates usam a sintaxe de templating do Go para gerar recursos Kubernetes dinamicamente. Esses templates podem gerar qualquer tipo de recurso Kubernetes, desde Deployments simples até StatefulSets complexos para aplicações com estado que requerem armazenamento persistente. Para aplicações que precisam de identidades estáveis e volumes persistentes, você deve usar StatefulSets em vez de Deployments, conforme detalhado em nosso guia sobre StatefulSets e Armazenamento Persistente no Kubernetes.
apiVersion: apps/v1
kind: Deployment
metadata:
name: {{ include "my-application.fullname" . }}
labels:
{{- include "my-application.labels" . | nindent 4 }}
spec:
{{- if not .Values.autoscaling.enabled }}
replicas: {{ .Values.replicaCount }}
{{- end }}
selector:
matchLabels:
{{- include "my-application.selectorLabels" . | nindent 6 }}
template:
metadata:
labels:
{{- include "my-application.selectorLabels" . | nindent 8 }}
spec:
containers:
- name: {{ .Chart.Name }}
image: "{{ .Values.image.repository }}:{{ .Values.image.tag | default .Chart.AppVersion }}"
imagePullPolicy: {{ .Values.image.pullPolicy }}
ports:
- containerPort: 8080
protocol: TCP
resources:
{{- toYaml .Values.resources | nindent 10 }}
Helpers de Template (_helpers.tpl)
Crie funções de template reutilizáveis para evitar repetições:
{{/*
Expanda o nome do chart.
*/}}
{{- define "my-application.name" -}}
{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" }}
{{- end }}
{{/*
Crie um nome de aplicação totalmente qualificado padrão.
*/}}
{{- define "my-application.fullname" -}}
{{- if .Values.fullnameOverride }}
{{- .Values.fullnameOverride | trunc 63 | trimSuffix "-" }}
{{- else }}
{{- $name := default .Chart.Name .Values.nameOverride }}
{{- printf "%s-%s" .Release.Name $name | trunc 63 | trimSuffix "-" }}
{{- end }}
{{- end }}
{{/*
Labels comuns
*/}}
{{- define "my-application.labels" -}}
helm.sh/chart: {{ include "my-application.chart" . }}
{{ include "my-application.selectorLabels" . }}
{{- if .Chart.AppVersion }}
app.kubernetes.io/version: {{ .Chart.AppVersion | quote }}
{{- end }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
{{- end }}
Gerenciando Helm Charts: Instalação e Operações
Instalando um Chart
# Instalar de um repositório
helm install my-release bitnami/postgresql
# Instalar de um diretório local
helm install my-app ./my-application
# Instalar com valores personalizados
helm install my-app ./my-application -f values-production.yaml
# Instalar com sobrescritas de valores inline
helm install my-app ./my-application \
--set replicaCount=5 \
--set image.tag=2.0.0
Atualizando Releases
# Atualizar com novos valores
helm upgrade my-app ./my-application -f values-production.yaml
# Atualizar com rollback atômico em caso de falha
helm upgrade my-app ./my-application --atomic --timeout 5m
# Forçar atualizações de recursos
helm upgrade my-app ./my-application --force
Rollback e Histórico
# Visualizar histórico de releases
helm history my-app
# Rollback para versão anterior
helm rollback my-app
# Rollback para revisão específica
helm rollback my-app 3
Testes e Depuração
# Dry-run para ver manifestos gerados
helm install my-app ./my-application --dry-run --debug
# Renderização de template sem instalação
helm template my-app ./my-application
# Lint do chart para problemas
helm lint ./my-application
# Testar release com ganchos de teste
helm test my-app
Recursos Avançados do Helm
Dependências de Chart
Helm Charts podem depender de outros Charts, permitindo que você componha aplicações complexas a partir de componentes reutilizáveis. Isso é particularmente útil ao implantar microsserviços que precisam de bancos de dados, filas de mensagens ou outros serviços de suporte. Defina dependências em Chart.yaml:
dependencies:
- name: redis
version: "17.x.x"
repository: "https://charts.bitnami.com/bitnami"
condition: redis.enabled
- name: postgresql
version: "12.x.x"
repository: "https://charts.bitnami.com/bitnami"
condition: postgresql.enabled
Atualizar dependências:
helm dependency update ./my-application
Hooks do Helm para Gerenciamento de Ciclo de Vida
Hooks são executados em pontos específicos do ciclo de vida do release:
apiVersion: batch/v1
kind: Job
metadata:
name: {{ include "my-application.fullname" . }}-db-migration
annotations:
"helm.sh/hook": pre-upgrade,pre-install
"helm.sh/hook-weight": "5"
"helm.sh/hook-delete-policy": before-hook-creation
spec:
template:
spec:
containers:
- name: db-migrate
image: "{{ .Values.image.repository }}:{{ .Values.image.tag }}"
command: ["python", "manage.py", "migrate"]
restartPolicy: Never
Tipos de hooks incluem:
pre-install: Antes que os recursos sejam instaladospost-install: Após todos os recursos serem instaladospre-upgrade: Antes da atualizaçãopost-upgrade: Após a atualizaçãopre-delete: Antes da exclusãopost-delete: Após a exclusãopre-rollback: Antes do rollbackpost-rollback: Após o rollback
Lógica Condicional e Controle de Fluxo
{{- if .Values.ingress.enabled }}
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: {{ include "my-application.fullname" . }}
{{- with .Values.ingress.annotations }}
annotations:
{{- toYaml . | nindent 4 }}
{{- end }}
spec:
{{- if .Values.ingress.className }}
ingressClassName: {{ .Values.ingress.className }}
{{- end }}
rules:
{{- range .Values.ingress.hosts }}
- host: {{ .host | quote }}
http:
paths:
{{- range .paths }}
- path: {{ .path }}
pathType: {{ .pathType }}
backend:
service:
name: {{ include "my-application.fullname" $ }}
port:
number: {{ $.Values.service.port }}
{{- end }}
{{- end }}
{{- end }}
Suporte a Registro OCI: Distribuição Moderna de Charts
Desde o Helm 3.8, o suporte a registro OCI (Open Container Initiative) é estável, permitindo que Charts sejam armazenados junto com imagens de contêiner.
Publicando em Registro OCI
# Login no registro
helm registry login registry.example.com
# Empacotar o chart
helm package ./my-application
# Push para registro OCI
helm push my-application-1.0.0.tgz oci://registry.example.com/charts
# Instalar de registro OCI
helm install my-app oci://registry.example.com/charts/my-application --version 1.0.0
Benefícios de Registros OCI
- Armazenamento Unificado: Charts e imagens em um só lugar
- Ferramentas Padrão: Usar infraestrutura de registro existente
- Melhor Segurança: Aproveitar autenticação e varredura do registro
- Gerenciamento Simples: Nenhum servidor de repositório de Chart separado necessário
Melhores Práticas para Helm Charts em Produção
1. Estrutura e Documentação de Valores
Documente todos os valores com comentários:
# -- Número de réplicas para a aplicação
replicaCount: 3
# -- Configuração de imagem
image:
# -- Repositório de imagem
repository: myapp/backend
# -- Política de pull de imagem
pullPolicy: IfNotPresent
# -- Tag de imagem (padrão é appVersion do chart)
tag: ""
2. Gerenciamento de Recursos
Sempre defina solicitações e limites de recursos:
resources:
limits:
cpu: 1000m
memory: 1Gi
requests:
cpu: 500m
memory: 512Mi
3. Contextos de Segurança
Defina contextos de segurança para contêineres:
securityContext:
runAsNonRoot: true
runAsUser: 1000
fsGroup: 1000
capabilities:
drop:
- ALL
readOnlyRootFilesystem: true
4. Verificações de Saúde
Inclua sondas de liveness e readiness:
livenessProbe:
httpGet:
path: /health
port: 8080
initialDelaySeconds: 30
periodSeconds: 10
readinessProbe:
httpGet:
path: /ready
port: 8080
initialDelaySeconds: 5
periodSeconds: 5
5. Gerenciamento de ConfigMap e Secret
O gerenciamento adequado de segredos é crítico para implantações em produção. Use gerencadores de segredos externos (Sealed Secrets, External Secrets Operator ou Vault) em vez de armazenar segredos em arquivos de valores. Isso garante que dados sensíveis como senhas de banco de dados, chaves de API e certificados sejam manipulados com segurança:
envFrom:
- secretRef:
name: {{ include "my-application.fullname" . }}-secrets
- configMapRef:
name: {{ include "my-application.fullname" . }}-config
6. Validação de Schema
Crie values.schema.json para validar entradas do usuário:
{
"$schema": "https://json-schema.org/draft-07/schema#",
"properties": {
"replicaCount": {
"type": "integer",
"minimum": 1
},
"image": {
"type": "object",
"properties": {
"repository": {
"type": "string"
},
"tag": {
"type": "string"
}
},
"required": ["repository"]
}
},
"required": ["image"]
}
7. NOTES.txt para Orientação do Usuário
Forneça instruções pós-instalação:
1. Obtenha a URL da aplicação executando:
{{- if .Values.ingress.enabled }}
https://{{ (index .Values.ingress.hosts 0).host }}
{{- else if contains "NodePort" .Values.service.type }}
export NODE_PORT=$(kubectl get --namespace {{ .Release.Namespace }} -o jsonpath="{.spec.ports[0].nodePort}" services {{ include "my-application.fullname" . }})
export NODE_IP=$(kubectl get nodes --namespace {{ .Release.Namespace }} -o jsonpath="{.items[0].status.addresses[0].address}")
echo http://$NODE_IP:$NODE_PORT
{{- end }}
2. Monitore a implantação:
kubectl --namespace {{ .Release.Namespace }} get pods -l "app.kubernetes.io/name={{ include "my-application.name" . }}"
Teste de Helm Charts e Integração CI/CD
Teste de Chart com chart-testing (ct)
# Instalar chart-testing
brew install chart-testing
# Lint de charts
ct lint --config ct.yaml
# Instalar e testar charts
ct install --config ct.yaml
Exemplo de GitHub Actions
name: Helm Chart CI
on:
push:
branches: [main]
pull_request:
branches: [main]
jobs:
lint-test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
with:
fetch-depth: 0
- name: Set up Helm
uses: azure/setup-helm@v3
with:
version: 3.12.0
- name: Set up chart-testing
uses: helm/chart-testing-action@v2
- name: Lint charts
run: ct lint --config ct.yaml
- name: Create kind cluster
uses: helm/kind-action@v1
- name: Install charts
run: ct install --config ct.yaml
GitOps com Helm: ArgoCD e Flux
Ferramentas GitOps como ArgoCD e Flux integram-se perfeitamente com Helm Charts, permitindo implantações declarativas e automatizadas. Essas ferramentas monitoram seu repositório Git por alterações e sincronizam automaticamente releases Helm, tornando a implantação contínua simples. Para arquiteturas de microsserviços complexas, considere como padrões de transação distribuída como o padrão Saga podem ajudar a gerenciar a consistência entre serviços implantados via Helm.
Aplicação ArgoCD
apiVersion: argoproj.io/v1alpha1
kind: Application
metadata:
name: my-application
namespace: argocd
spec:
project: default
source:
repoURL: https://github.com/myorg/my-app-chart
targetRevision: main
path: charts/my-application
helm:
valueFiles:
- values-production.yaml
destination:
server: https://kubernetes.default.svc
namespace: production
syncPolicy:
automated:
prune: true
selfHeal: true
Flux HelmRelease
apiVersion: helm.toolkit.fluxcd.io/v2beta1
kind: HelmRelease
metadata:
name: my-application
namespace: flux-system
spec:
interval: 5m
chart:
spec:
chart: my-application
version: '1.x.x'
sourceRef:
kind: HelmRepository
name: my-charts
values:
replicaCount: 5
image:
tag: "2.0.0"
Solução de Problemas Comuns do Helm
Problema: Atualização Falhada Presa em Pendente
# Verificar status do release
helm list --all-namespaces
# Obter detalhes do release
helm status my-app -n namespace
# Forçar exclusão se necessário (use com cuidado)
kubectl delete secret -n namespace -l owner=helm,name=my-app
Problema: Erros de Renderização de Template
# Depurar renderização de template
helm template my-app ./my-application --debug
# Validar contra Kubernetes
helm template my-app ./my-application | kubectl apply --dry-run=client -f -
Problema: Valores Não Aplicados
# Verificar valores mesclados
helm get values my-app
# Mostrar todos os valores computados
helm get values my-app --all
Ecossistema e Ferramentas do Helm
O ecossistema do Helm inclui inúmeras ferramentas que estendem suas capacidades e integram-se com outras tecnologias Kubernetes. Ao implantar aplicações que requerem recursos avançados de rede como comunicação serviço-a-serviço, gerenciamento de tráfego e políticas de segurança, considere integrar com uma Service Mesh com Istio e Linkerd, que pode ser implantada e gerenciada através de Helm Charts.
Ferramentas Essenciais
- Helmfile: Especificação declarativa para implantar Helm Charts
- Helm Diff: Pré-visualizar alterações antes da atualização
- Helm Secrets: Gerenciar segredos com SOPS
- Nova: Encontrar Helm Charts desatualizados
- Pluto: Detectar APIs Kubernetes depreciadas
Exemplo de Helmfile
repositories:
- name: bitnami
url: https://charts.bitnami.com/bitnami
releases:
- name: postgresql
namespace: database
chart: bitnami/postgresql
version: 12.x.x
values:
- postgresql:
auth:
database: myapp
username: appuser
- name: my-app
namespace: production
chart: ./charts/my-application
values:
- values-production.yaml
needs:
- database/postgresql
O Futuro do Helm
O ecossistema do Helm continua evoluindo:
- Nativo OCI: Transição completa para registros OCI como padrão
- Segurança Melhorada: Melhor gerenciamento de segredos e capacidades de assinatura
- Desempenho: Renderização e instalação mais rápidas para Charts grandes
- Suporte WASM: WebAssembly para plugins e extensões de Chart
- Validação Melhorada: Validação de schema aprimorada e aplicação de políticas
Conclusão
O Helm tornou-se o padrão de facto para gerenciamento de pacotes Kubernetes, e dominá-lo é essencial para práticas modernas de DevOps. Ao compreender a estrutura de Charts, templating, gerenciamento de valores e melhores práticas, você pode criar implantações Kubernetes mantíveis, seguras e escaláveis.
Comece com Charts simples, incorpore gradualmente recursos avançados como hooks e dependências, e integre com ferramentas GitOps para infraestrutura de nível de produção. A comunidade do Helm fornece milhares de Charts pré-construídos, mas o verdadeiro poder vem da criação de Charts personalizados adaptados às necessidades da sua organização. Seja você esteja implantando aplicações stateless ou cargas de trabalho com estado que requerem armazenamento persistente, o Helm simplifica a complexidade do gerenciamento de recursos Kubernetes. Para equipes configurando novos clusters Kubernetes, considere instalar Kubernetes com Kubespray ou explorar distribuições Kubernetes como k3s ou MicroK8s para ambientes de desenvolvimento. Se você estiver avaliando qual distribuição se adequa às suas necessidades de homelab ou cluster pequeno, veja nossa comparação abrangente de distribuições Kubernetes para uma análise detalhada.
Links Úteis
- Documentação Oficial do Helm
- Artifact Hub - Descubra Helm Charts
- Repositório GitHub do Helm
- Guia de Melhores Práticas do Helm
- Ferramenta de Teste de Chart
- Helmfile
- ArgoCD
- Flux CD
- Repositório de Charts Bitnami
- Lista de Comandos do Kubernetes
- Instalar Kubernetes com Kubespray
- Comparação de Distribuições Kubernetes para um Homelab de 3 Nós
- Distribuições Kubernetes - visão geral rápida de kubeadm, k3s, MicroK8s, Minikube, Talos Linux e RKE2
- Service Mesh com Istio e Linkerd
- StatefulSets e Armazenamento Persistente no Kubernetes
- Padrão Saga em Transações Distribuídas