Post

Kubernetes: Configuração do MetalLB e do Gateway API - Parte 2

Kubernetes: Configuração do MetalLB e do Gateway API - Parte 2

Introdução

Na Parte 1, configuramos um cluster Kubernetes funcional com CRI-O e Calico com suporte a dual-stack. Porém, em ambientes on-premises, não temos acesso a load balancers gerenciados como AWS ELB ou Google Cloud Load Balancer.

O MetalLB resolve esse problema fornecendo um controlador de load balancing nativo do Kubernetes que funciona com hardware padrão. Além disso, o Gateway API é a evolução moderna do Ingress Controller, oferecendo um modelo mais flexível e poderoso para roteamento de tráfego.

Nesta parte, vamos implementar ambos os componentes para criar uma solução de ingress e load balancing robusta e pronta para produção.

O que será visto nesta parte

  • Instalação do Helm: Gerenciador de pacotes para Kubernetes.
  • Instalação e Configuração do MetalLB: Load balancing com suporte a dual-stack.
  • Instalação do Envoy Gateway: Implementação de Gateway API.
  • Configuração de Gateways e Routes: Roteamento de tráfego HTTP.
  • Testes e Validação: Verificação de funcionalidade.

Pré-requisitos

  • Cluster Kubernetes completamente funcional (conforme Parte 1).
  • Conhecimento básico de networking e Kubernetes.
  • Acesso ao cluster via kubectl.

Topologia de Rede

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
Internet / Rede Externa
        |
        | (IPs do MetalLB: 10.16.47.208/28, fd00::4:1000:0:0:70/124)
        |
    ┌───────────────────────────────────────────┐
    │   Cluster Kubernetes                      │
    │                                           │
    │  ┌─────────────────────────────────────┐  │
    │  │ MetalLB LoadBalancer                │  │
    │  │ (Gerencia IPs externos)             │  │
    │  └─────────────────────────────────────┘  │
    │           |                               │
    │  ┌────────┴────────┐                      │
    │  |                 |                      │
    │  ▼                 ▼                      │
    │ ┌──────────┐  ┌──────────┐                │
    │ │ Envoy    │  │ Envoy    │                │
    │ │ Gateway  │  │ Gateway  │                │
    │ │ (Ingress)│  │ (Ingress)│                │
    │ └──────────┘  └──────────┘                │
    │       |              |                    │
    │  ┌────┴──────────────┴────┐               │
    │  |                        |               │
    │  ▼                        ▼               │
    │ ┌──────────┐        ┌──────────┐          │
    │ │ Pods da  │        │ Pods da  │          │
    │ │ Aplicação│        │ Aplicação│          │
    │ └──────────┘        └──────────┘          │
    └───────────────────────────────────────────┘

1. Instalação do Helm

1.1 O que é Helm?

Helm é o gerenciador de pacotes para Kubernetes. Ele simplifica a instalação e gerenciamento de aplicações complexas através de charts (templates pré-configurados).

1.2 Instalação

1
2
3
4
5
# Baixar e executar o script de instalação
curl https://raw.githubusercontent.com/helm/helm/main/scripts/get-helm-4 | bash

# Verificar versão instalada
helm version --short

Saída esperada:

1
v4.1.0+g4553a0a

2. Instalação e Configuração do MetalLB

2.1 Conceitos Fundamentais

MetalLB é um controlador de load balancing que funciona em clusters Kubernetes on-premises. Ele fornece uma implementação de LoadBalancer para o tipo de serviço Kubernetes.

Como Funciona

  1. Alocação de IP: Quando um serviço do tipo LoadBalancer é criado, o MetalLB aloca um IP de um pool pré-configurado.
  2. Anúncio de IP: O MetalLB anuncia esse IP na rede usando Layer 2 (ARP).
  3. Roteamento de Tráfego: O tráfego destinado ao IP do LoadBalancer é roteado para os pods da aplicação.

2.2 Instalação do MetalLB

Adicione o repositório Helm do MetalLB:

1
2
helm repo add metallb https://metallb.github.io/metallb
helm repo update

Instale o MetalLB:

1
2
3
4
helm install metallb metallb/metallb \
  --create-namespace \
  --namespace metallb-system \
  --wait

Saída esperada:

1
2
3
4
5
6
NAME: metallb
LAST DEPLOYED: Sun Feb  8 17:29:54 2026
NAMESPACE: metallb-system
STATUS: deployed
REVISION: 1
DESCRIPTION: Install complete

2.3 Verificação da Instalação

1
2
# Verificar se os pods estão em execução
kubectl get pods -n metallb-system -o wide

Saída esperada:

1
2
3
4
5
NAME                                  READY   STATUS    RESTARTS   AGE   IP              NODE           NOMINATED NODE   READINESS GATES
metallb-controller-84c7d4d544-q45lh   1/1     Running   0          13m   10.80.213.195   kube-wk-02     <none>           <none>
metallb-speaker-6nr9c                 4/4     Running   0          13m   10.16.47.2      kube-ctrl-01   <none>           <none>
metallb-speaker-nf4vs                 4/4     Running   0          13m   10.16.47.10     kube-wk-01     <none>           <none>
metallb-speaker-sm6gv                 4/4     Running   0          13m   10.16.47.11     kube-wk-02     <none>           <none>

2.4 Configuração de Pool de Endereços Dual-Stack

Crie um arquivo metallb-config.yaml:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
apiVersion: metallb.io/v1beta1
kind: IPAddressPool
metadata:
  name: dualstack-pool
  namespace: metallb-system
spec:
  addresses:
    - 10.16.47.208/28
    - fd00::4:1000:0:0:70/124
  avoidBuggyIPs: true

---
apiVersion: metallb.io/v1beta1
kind: L2Advertisement
metadata:
  name: l2-advertisement
  namespace: metallb-system
spec:
  ipAddressPools:
    - dualstack-pool

Aplique a configuração:

1
kubectl apply -f metallb-config.yaml

2.5 Verificação da Configuração

1
2
# Verificar pools de IP
kubectl get IPAddressPool -n metallb-system

Saída esperada:

1
2
NAME             AUTO ASSIGN   AVOID BUGGY IPS   ADDRESSES
dualstack-pool   true          true              ["10.16.47.208/28","fd00::4:1000:0:0:70/124"]

Verifique detalhes do pool:

1
kubectl describe IPAddressPool dualstack-pool -n metallb-system

3. Instalação e Configuração do Envoy Gateway

3.1 Conceitos Fundamentais do Gateway API

O Gateway API é a evolução moderna do Ingress Controller. Oferece um modelo mais flexível e poderoso para roteamento de tráfego, com suporte a múltiplos protocolos (HTTP, HTTPS, TCP, UDP) e roteamento avançado.

3.2 Instalação do Envoy Gateway

Instale o Envoy Gateway via Helm:

1
2
3
4
helm install eg oci://docker.io/envoyproxy/gateway-helm \
  --version v1.6.0 \
  -n envoy-gateway-system \
  --create-namespace

Saída esperada:

1
2
3
4
5
6
NAME: eg
LAST DEPLOYED: Sun Feb  8 17:52:22 2026
NAMESPACE: envoy-gateway-system
STATUS: deployed
REVISION: 1
DESCRIPTION: Install complete

3.3 Verificação da Instalação

1
2
# Verificar pods
kubectl get pods -n envoy-gateway-system

Saída esperada:

1
2
NAME                                 READY   STATUS    RESTARTS   AGE
pod/envoy-gateway-77cf8577fd-vmrrg   1/1     Running   0          46s

Verifique todos os recursos:

1
kubectl get all -n envoy-gateway-system

4. Configuração do Envoy Gateway para Dual-Stack

4.1 Criação da GatewayClass

Crie um arquivo gateway-class.yaml:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
apiVersion: gateway.envoyproxy.io/v1alpha1
kind: EnvoyProxy
metadata:
  name: dual-stack-proxy
  namespace: envoy-gateway-system
spec:
  ipFamily: DualStack

---
apiVersion: gateway.networking.k8s.io/v1
kind: GatewayClass
metadata:
  name: envoy-gateway-class
spec:
  controllerName: gateway.envoyproxy.io/gatewayclass-controller
  parametersRef:
    group: gateway.envoyproxy.io
    kind: EnvoyProxy
    name: dual-stack-proxy
    namespace: envoy-gateway-system

Aplique:

1
kubectl apply -f gateway-class.yaml

4.2 Criação do Gateway

Crie um arquivo gateway.yaml:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
apiVersion: gateway.networking.k8s.io/v1
kind: Gateway
metadata:
  name: main-gateway
  namespace: envoy-gateway-system
spec:
  gatewayClassName: envoy-gateway-class
  listeners:
    - name: http
      protocol: HTTP
      port: 80
      allowedRoutes:
        namespaces:
          from: All

Aplique:

1
kubectl apply -f gateway.yaml

4.3 Verificação do Gateway

1
2
# Verificar status do Gateway
kubectl get gateway main-gateway -n envoy-gateway-system

Saída esperada:

1
2
NAME           CLASS                 ADDRESS        PROGRAMMED   AGE
main-gateway   envoy-gateway-class   10.16.47.208   False        7s

Verifique o serviço criado:

1
kubectl get svc -n envoy-gateway-system

Saída esperada:

1
2
3
NAME                                               TYPE           CLUSTER-IP     EXTERNAL-IP                        PORT(S)                                            AGE
envoy-envoy-gateway-system-main-gateway-c3508b54   LoadBalancer   10.96.44.131   10.16.47.208,fd00::4:1000:0:0:70   80:32180/TCP                                       14s
envoy-gateway                                      ClusterIP      10.96.132.0    <none>                             18000/TCP,18001/TCP,18002/TCP,19001/TCP,9443/TCP   4m57s

5. Exemplo Prático Completo

5.1 Implantação de Aplicação de Teste

Crie um arquivo app-teste.yaml:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx-teste
  namespace: default
spec:
  replicas: 2
  selector:
    matchLabels:
      app: nginx-teste
  template:
    metadata:
      labels:
        app: nginx-teste
    spec:
      containers:
      - name: nginx
        image: nginx:alpine
        ports:
        - containerPort: 80

---
apiVersion: v1
kind: Service
metadata:
  name: nginx-servico
  namespace: default
spec:
  selector:
    app: nginx-teste
  ports:
    - protocol: TCP
      port: 80
      targetPort: 80
  type: ClusterIP

Aplique:

1
kubectl apply -f app-teste.yaml

5.2 Criação da HTTPRoute

Crie um arquivo httproute-teste.yaml:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
  name: rota-nginx
  namespace: default
spec:
  parentRefs:
  - name: main-gateway
    namespace: envoy-gateway-system
  hostnames:
  - "meuapp.lab4it.com.br"
  rules:
  - matches:
    - path:
        type: PathPrefix
        value: /
    backendRefs:
    - name: nginx-servico
      port: 80

Aplique:

1
kubectl apply -f httproute-teste.yaml

5.3 Verificação da Rota

1
2
# Verificar HTTPRoute
kubectl get httproute

Saída esperada:

1
2
NAME         HOSTNAMES                  AGE
rota-nginx   ["meuapp.lab4it.com.br"]   14m

5.4 Teste de Conectividade

Teste a conectividade via IPv4:

1
curl -H "Host: meuapp.lab4it.com.br" http://10.16.47.208

Teste a conectividade via IPv6:

1
curl -g -H "Host: meuapp.lab4it.com.br" "http://[fd00::4:1000:0:0:70]"

Saída esperada (ambos os casos):

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
html { color-scheme: light dark; }
body { width: 35em; margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif; }
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>
</body>
</html>

6. Solucionando Problemas Comuns

Sintoma ObservadoProblemaCausa ProvávelSolução
MetalLB não aloca IP para LoadBalancerPool de IP não configuradoIPAddressPool não foi criado ou está vazio.Verifique kubectl get ipaddresspool -n metallb-system e confirme que o pool está configurado.
Gateway não recebe endereçoEnvoy Gateway não está prontoPods do Envoy Gateway não estão em execução.Verifique kubectl get pods -n envoy-gateway-system e verifique logs com kubectl logs -n envoy-gateway-system.
HTTPRoute não roteia tráfegoRota não está associada ao GatewayNome do Gateway ou namespace incorreto.Verifique kubectl describe httproute <nome> e confirme parentRefs.
Tráfego lentoMuitos hops de redeRoteamento ineficiente.Verifique topologia de rede e considere usar BGP em vez de Layer 2.
Serviço LoadBalancer fica com EXTERNAL-IP <pending>MetalLB não consegue alocar IPPool de IP esgotado ou não configurado.Verifique kubectl describe svc <nome> para ver eventos de erro.

Conclusão

Com MetalLB e Gateway API configurados, você agora possui uma solução completa de ingress e load balancing para seu cluster Kubernetes on-premises. O MetalLB fornece endereços IP externos para serviços, enquanto o Gateway API oferece roteamento avançado e flexível para tráfego HTTP/HTTPS com suporte a dual-stack.

Essa combinação oferece uma alternativa robusta aos serviços gerenciados de nuvem, permitindo que você execute cargas de trabalho de produção em ambientes on-premises com confiabilidade e escalabilidade.

Na Parte 3, vamos implementar o NFS para armazenamento persistente.


Próximos Passos

Clique aqui para ir para Kubernetes: Configuração do NFS - Parte 3


Referências

This post is licensed under CC BY 4.0 by the author.