Home > Blog > Desenvolvimento Web
Desenvolvimento Web
JavaScript
Programação

Helm para Node.js

Atualizado em: 19 de setembro de 2026

Terminal Linux usado em desenvolvimento e administração de aplicações Node.js

O Helm para Node.js empacota recursos Kubernetes em um chart versionado e configurável. Em vez de duplicar arquivos Deployment, Service, HPA, ConfigMap e Ingress para cada ambiente, a equipe mantém templates e fornece valores diferentes para desenvolvimento, homologação e produção.

Helm não substitui o entendimento do Kubernetes. Um chart pode gerar manifestos válidos e ainda criar uma aplicação insegura, sem probes ou com selectors incorretos. O objetivo é reduzir repetição, validar configurações e controlar releases, sem esconder as decisões operacionais.

Neste guia, você aprenderá a criar um chart para uma API Node.js, organizar Chart.yaml, values, templates, helpers, schema, secrets, upgrades, rollback, testes e publicação em registry OCI.

O que é um chart?

A documentação oficial de charts do Helm define chart como uma coleção de arquivos que descreve recursos relacionados do Kubernetes. A estrutura básica é:

orders-api/
├── Chart.yaml
├── values.yaml
├── values.schema.json
├── templates/
│   ├── _helpers.tpl
│   ├── deployment.yaml
│   ├── service.yaml
│   ├── hpa.yaml
│   ├── ingress.yaml
│   ├── serviceaccount.yaml
│   ├── configmap.yaml
│   ├── NOTES.txt
│   └── tests/
└── .helmignore

Criando o chart

helm create orders-api

O comando gera um exemplo genérico. Remova templates que não fazem parte do serviço e adapte os nomes, labels e valores.

Chart.yaml

apiVersion: v2
name: orders-api
description: API de pedidos em Node.js
type: application
version: 0.1.0
appVersion: "1.4.3"
kubeVersion: ">=1.30.0-0"

version é a versão do chart. appVersion documenta a versão da aplicação, mas não altera automaticamente a imagem. Use SemVer e incremente o chart sempre que templates ou defaults mudarem.

values.yaml

replicaCount: 3

image:
  repository: registry.example.com/orders-api
  tag: "1.4.3"
  pullPolicy: IfNotPresent

service:
  type: ClusterIP
  port: 80
  targetPort: 3000

resources:
  requests:
    cpu: 250m
    memory: 256Mi
  limits:
    cpu: 1
    memory: 512Mi

config:
  nodeEnv: production
  port: 3000

autoscaling:
  enabled: true
  minReplicas: 3
  maxReplicas: 20
  targetCPUUtilizationPercentage: 60

Defaults devem ser seguros. Não coloque senhas ou tokens no values versionado.

Helpers de nomes

Em templates/_helpers.tpl:

{{- define "orders-api.name" -}}
{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" }}
{{- end }}

{{- define "orders-api.fullname" -}}
{{- if .Values.fullnameOverride }}
{{- .Values.fullnameOverride | trunc 63 | trimSuffix "-" }}
{{- else }}
{{- printf "%s-%s" .Release.Name (include "orders-api.name" .) | trunc 63 | trimSuffix "-" }}
{{- end }}
{{- end }}

Helpers evitam repetir lógica e mantêm nomes consistentes.

Labels recomendadas

{{- define "orders-api.labels" -}}
helm.sh/chart: {{ .Chart.Name }}-{{ .Chart.Version | replace "+" "_" }}
app.kubernetes.io/name: {{ include "orders-api.name" . }}
app.kubernetes.io/instance: {{ .Release.Name }}
app.kubernetes.io/version: {{ .Chart.AppVersion | quote }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
{{- end }}

Selectors devem usar apenas labels estáveis. Não inclua chart version no selector, pois ele mudaria durante upgrade.

Deployment template

apiVersion: apps/v1
kind: Deployment
metadata:
  name: {{ include "orders-api.fullname" . }}
  labels:
    {{- include "orders-api.labels" . | nindent 4 }}
spec:
  {{- if not .Values.autoscaling.enabled }}
  replicas: {{ .Values.replicaCount }}
  {{- end }}
  selector:
    matchLabels:
      app.kubernetes.io/name: {{ include "orders-api.name" . }}
      app.kubernetes.io/instance: {{ .Release.Name }}
  template:
    metadata:
      labels:
        app.kubernetes.io/name: {{ include "orders-api.name" . }}
        app.kubernetes.io/instance: {{ .Release.Name }}
    spec:
      serviceAccountName: {{ include "orders-api.fullname" . }}
      securityContext:
        runAsNonRoot: true
        seccompProfile:
          type: RuntimeDefault
      containers:
        - name: api
          image: "{{ .Values.image.repository }}:{{ .Values.image.tag }}"
          imagePullPolicy: {{ .Values.image.pullPolicy }}
          ports:
            - name: http
              containerPort: {{ .Values.service.targetPort }}
          resources:
            {{- toYaml .Values.resources | nindent 12 }}

Veja Kubernetes Deployment no Node.js.

Probes

probes:
  readiness:
    path: /health/ready
    initialDelaySeconds: 2
  liveness:
    path: /health/live
    initialDelaySeconds: 10

No template:

readinessProbe:
  httpGet:
    path: {{ .Values.probes.readiness.path | quote }}
    port: http
  initialDelaySeconds: {{ .Values.probes.readiness.initialDelaySeconds }}
livenessProbe:
  httpGet:
    path: {{ .Values.probes.liveness.path | quote }}
    port: http
  initialDelaySeconds: {{ .Values.probes.liveness.initialDelaySeconds }}

Consulte Probes Kubernetes em Node.js.

ConfigMap

apiVersion: v1
kind: ConfigMap
metadata:
  name: {{ include "orders-api.fullname" . }}
data:
  NODE_ENV: {{ .Values.config.nodeEnv | quote }}
  PORT: {{ .Values.config.port | quote }}

Monte por envFrom ou variáveis específicas. Uma alteração no ConfigMap não reinicia automaticamente o Deployment.

Checksum para rollout

template:
  metadata:
    annotations:
      checksum/config: {{ include (print $.Template.BasePath "/configmap.yaml") . | sha256sum }}

Quando o conteúdo renderizado muda, a annotation muda e o Deployment cria novos Pods.

Secrets

Evite gerar Secret com valor em texto claro dentro de values.yaml. Prefira External Secrets, Sealed Secrets ou integração com o provedor. O chart pode receber o nome de um Secret existente:

existingSecret: orders-api-secrets
envFrom:
  - secretRef:
      name: {{ required "existingSecret é obrigatório" .Values.existingSecret }}

Veja ConfigMaps e Secrets no Node.js.

Service

apiVersion: v1
kind: Service
metadata:
  name: {{ include "orders-api.fullname" . }}
spec:
  type: {{ .Values.service.type }}
  selector:
    app.kubernetes.io/name: {{ include "orders-api.name" . }}
    app.kubernetes.io/instance: {{ .Release.Name }}
  ports:
    - name: http
      port: {{ .Values.service.port }}
      targetPort: http

HPA

{{- if .Values.autoscaling.enabled }}
apiVersion: autoscaling/v2
kind: HorizontalPodAutoscaler
metadata:
  name: {{ include "orders-api.fullname" . }}
spec:
  scaleTargetRef:
    apiVersion: apps/v1
    kind: Deployment
    name: {{ include "orders-api.fullname" . }}
  minReplicas: {{ .Values.autoscaling.minReplicas }}
  maxReplicas: {{ .Values.autoscaling.maxReplicas }}
  metrics:
    - type: Resource
      resource:
        name: cpu
        target:
          type: Utilization
          averageUtilization: {{ .Values.autoscaling.targetCPUUtilizationPercentage }}
{{- end }}

Quando HPA está ativo, o template omite replicas. Veja Kubernetes HPA no Node.js.

Values por ambiente

values.yaml
values-development.yaml
values-staging.yaml
values-production.yaml

O arquivo base contém defaults. Os ambientes sobrescrevem apenas diferenças:

helm upgrade --install orders-api ./orders-api \
  --namespace production \
  --create-namespace \
  --values values-production.yaml

Evite excesso de parâmetros

Um chart com centenas de flags vira uma linguagem própria. Exponha valores que realmente variam entre instalações e mantenha invariantes de segurança no template.

values.schema.json

A documentação oficial permite validar values com JSON Schema:

{
  "$schema": "https://json-schema.org/draft-07/schema#",
  "type": "object",
  "required": ["image", "resources", "existingSecret"],
  "properties": {
    "replicaCount": {
      "type": "integer",
      "minimum": 1,
      "maximum": 100
    },
    "image": {
      "type": "object",
      "required": ["repository", "tag"],
      "properties": {
        "repository": {"type": "string", "minLength": 1},
        "tag": {"type": "string", "minLength": 1}
      }
    }
  }
}

Schema detecta valores ausentes e tipos errados antes da instalação.

required e fail

{{ required "image.repository é obrigatório" .Values.image.repository }}

Use validação explícita para invariantes que JSON Schema não expressa facilmente.

Renderização local

helm template orders-api ./orders-api \
  --namespace production \
  --values values-production.yaml

Inspecione o YAML gerado antes de aplicar. Isso ajuda a encontrar indentation, valores vazios e APIs incorretas.

Lint

helm lint ./orders-api \
  --values values-production.yaml \
  --strict

Lint deve fazer parte do CI, mas não substitui validação contra schemas Kubernetes.

Validação no CI

helm dependency build ./orders-api
helm lint ./orders-api --strict
helm template orders-api ./orders-api \
  --values values-production.yaml \
  | kubeconform -strict -summary

Também execute scanners de política, segurança e APIs depreciadas.

Dry-run no servidor

helm upgrade --install orders-api ./orders-api \
  --namespace production \
  --values values-production.yaml \
  --dry-run=server

O dry-run local não conhece todos os recursos e admission policies do cluster. O modo servidor oferece validação adicional, mas não deve expor secrets nos logs.

Upgrade atômico

helm upgrade --install orders-api ./orders-api \
  --namespace production \
  --values values-production.yaml \
  --atomic \
  --wait \
  --timeout 10m

--atomic tenta desfazer uma atualização que falha. --wait aguarda recursos ficarem prontos. Migrations e sistemas externos ainda precisam de estratégia própria.

Histórico e rollback

helm history orders-api -n production
helm rollback orders-api 7 -n production --wait

Rollback restaura manifestos da release. Ele não desfaz dados, filas ou migrations. Use mudanças de banco compatíveis.

Hooks

Hooks podem executar Jobs antes ou depois do upgrade:

metadata:
  annotations:
    helm.sh/hook: pre-upgrade
    helm.sh/hook-weight: "0"
    helm.sh/hook-delete-policy: before-hook-creation,hook-succeeded

Hooks de migration podem bloquear e tornar rollback complexo. Prefira um pipeline explícito quando o processo exige controle detalhado.

Chart tests

apiVersion: v1
kind: Pod
metadata:
  name: "{{ include "orders-api.fullname" . }}-test"
  annotations:
    helm.sh/hook: test
spec:
  restartPolicy: Never
  containers:
    - name: curl
      image: curlimages/curl:8.12.1
      command:
        - curl
        - --fail
        - http://{{ include "orders-api.fullname" . }}/health/live
helm test orders-api -n production

Dependências

dependencies:
  - name: redis
    version: "20.6.1"
    repository: "https://charts.bitnami.com/bitnami"
    condition: redis.enabled

Fixe versões e execute helm dependency update. Para serviços de produção, bancos e caches gerenciados separadamente costumam ter ciclo de vida diferente da API.

OCI registry

Charts podem ser armazenados em registries OCI:

helm package ./orders-api
helm push orders-api-0.1.0.tgz oci://registry.example.com/charts

Instalação:

helm upgrade --install orders-api \
  oci://registry.example.com/charts/orders-api \
  --version 0.1.0

Assinatura e provenance

Verifique origem e integridade de charts distribuídos. A documentação de provenance do Helm explica arquivos de assinatura e verificação. Em registries OCI, combine controles do registry, digest e ferramentas de assinatura.

Observabilidade da release

helm list -n production
helm status orders-api -n production
helm get values orders-api -n production
helm get manifest orders-api -n production

Registre chart version, app version, image digest e revisão da release.

Erros comuns

  • Selector usa versão: upgrade deixa de encontrar os Pods.
  • Secrets no values: credenciais vazam no Git ou histórico.
  • Tag latest: release não é reproduzível.
  • Sem schema: tipos inválidos chegam ao template.
  • Parâmetros demais: o chart fica impossível de manter.
  • Hook de migration inseguro: rollback não recupera o banco.
  • Confiar apenas no lint: políticas do cluster não são testadas.
  • Chart e app com mesma versão: ciclos independentes ficam confusos.

Conclusão

O Helm para Node.js organiza manifestos Kubernetes em charts versionados, com values, templates, schema, releases e rollback. A ferramenta reduz repetição e facilita configurar ambientes, mas os recursos gerados continuam exigindo boas práticas do Kubernetes.

Mantenha defaults seguros, selectors estáveis e secrets externos. Valide com lint, template, schema e políticas no CI. Use upgrades atômicos com observabilidade e trate migrations separadamente. Assim, o chart se torna um pacote previsível para entregar aplicações Node.js.

10 melhores cursos de programação em 2026

Descubra os melhores cursos de programação. Aprenda a escolher o curso ideal para iniciar ou avançar na carreira de desenvolvedor

POSTS RELACIONADOS

Ver todos

Seta para a direita