O que é Docker Swarm e por que usá-lo?
Docker Swarm é a ferramenta de orquestração nativa do Docker. Diferente de outras soluções complexas, o Swarm permite agrupar múltiplos servidores (nós) em um único cluster virtual, gerenciando serviços distribuídos automaticamente. Para ambientes que rodam em múltiplas VPS, o Swarm oferece alta disponibilidade, escalabilidade horizontal e failover automático sem a sobrecarga de gerenciar máquinas virtuais pesadas.
Neste tutorial, vamos configurar um cluster básico com três nós: um Manager (gerenciador) e dois Workers (trabalhadores). Utilizaremos uma arquitetura padrão que inclui balanceamento de carga, SSL automático via Let's Encrypt e atualização contínua de imagens.
Pré-requisitos e Instalação do Docker
Antes de iniciar o Swarm, precisamos garantir que todos os nós tenham o Docker instalado corretamente. A instalação docker deve ser consistente em todas as máquinas para evitar conflitos de versão.
- Acesse cada uma das suas VPS via SSH.
- Atualize o índice do pacote e instale as dependências necessárias:
sudo apt-get update
sudo apt-get install ca-certificates curl gnupg lsb-release -y
- Adicione a chave GPG oficial do Docker e o repositório:
sudo mkdir -p /etc/apt/keyrings
curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmor -o /etc/apt/keyrings/docker.gpg
echo "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.gpg] https://download.docker.com/linux/ubuntu $(lsb_release -cs) stable" | sudo tee /etc/apt/sources.list.d/docker.list
- Instale o Docker Engine:
sudo apt-get update
sudo apt-get install docker-ce docker-ce-cli containerd.io -y
Repita este processo em todos os três servidores. Verifique a instalação com docker --version.
Iniciando o Cluster Docker Swarm
O primeiro passo é inicializar o Swarm no nó Manager. Escolha uma VPS para ser o coração do cluster (geralmente a que terá maior capacidade de processamento e armazenamento).
- No nó Manager, execute:
docker swarm init --advertise-addr <IP_DO_MANAGER>
O comando retornará uma string longa começando com docker swarm join --token .... Copie essa string, pois ela será usada para adicionar os nós Workers.
- Nos nós Workers, execute o comando de junção retornado no passo anterior:
docker swarm join --token <TOKEN_RETORNADO> <IP_DO_MANAGER>:2377
Para verificar se os nós estão conectados, volte ao Manager e execute:
docker node ls
Você deve ver três nós listados. O Manager terá o status "Ready" e a etiqueta "Leader".
Criando Redes Docker para Isolamento
A segurança e a comunicação interna dependem de uma configuração robusta de redes docker. No Swarm, utilizamos redes overlay que permitem que containers em diferentes nós se comuniquem via DNS interno.
- Crie uma rede privada para serviços internos (ex: banco de dados, cache):
docker network create --driver overlay --attachable backend-net
- Crie uma rede pública para exposição externa:
docker network create --driver overlay --attachable frontend-net
A flag --attachable é crucial, pois permite que serviços não gerenciados pelo Swarm (como contêineres de proxy) se conectem a essas redes.
Deploy do Traefik como Reverse Proxy
O Traefik reverse proxy é o componente central que roteia o tráfego HTTP/HTTPS para seus serviços. Ele lida com o SSL e descobre os serviços automaticamente através das labels do Docker.
- Crie um arquivo
traefik.ymlno Manager:
global:
checkNewVersion: true
sendAnonymousUsage: false
providers:
docker:
endpoint: "unix:///var/run/docker.sock"
exposedByDefault: false
network: frontend-net
file:
filename: /etc/traefik/dynamic.yml
entryPoints:
web:
address: ":80"
websecure:
address: ":443"
certificatesResolvers:
letsencrypt:
acme:
email: "[email protected]"
storage: /etc/traefik/acme.json
httpChallenge:
entryPoint: web
- Crie o arquivo
dynamic.ymlpara configurações dinâmicas:
http:
middlewares:
securityHeaders:
headers:
stsSeconds: 31536000
- Crie um volume para armazenar o certificado SSL:
docker volume create traefik-acme
- Deploy do serviço Traefik no Swarm:
docker service create \
--name traefik \
--publish 80:80 \
--publish 443:443 \
--constraint=node.role==manager \
--mount type=bind,source=/var/run/docker.sock,target=/var/run/docker.sock \
--mount type=bind,source=$(pwd)/traefik.yml,target=/etc/traefik/traefik.yml \
--mount type=bind,source=$(pwd)/dynamic.yml,target=/etc/traefik/dynamic.yml \
--mount type=volume,source=traefik-acme,target=/etc/traefik/acme.json \
--network frontend-net \
--restart-condition any \
traefik:latest \
--providers.docker \
--providers.docker.swarmmode \
--providers.file.filename=/etc/traefik/dynamic.yml \
--entrypoints.web.address=:80 \
--entrypoints.websecure.address=:443 \
--certificatesresolvers.letsencrypt.acme.email=seu-email@exemplo.com \
--certificatesresolvers.letsencrypt.acme.storage=/etc/traefik/acme.json \
--certificatesresolvers.letsencrypt.acme.httpchallenge.entrypoint=web
Agora o Traefik está escutando nas portas 80 e 443 e configurado para obter SSL automatico via Let's Encrypt.
Deploy de Aplicação com SSL Automático
Vamos criar um serviço simples (ex: Nginx) para testar a integração. Ao adicionar labels específicas, o Traefik irá automaticamente gerar certificados e rotear o tráfego.
docker service create \
--name nginx-teste \
--network frontend-net \
--label traefik.enable=true \
--label "traefik.http.routers.nginx.rule=Host(\`app.seudominio.com\`)" \
--label "traefik.http.routers.nginx.entrypoints=websecure" \
--label "traefik.http.routers.nginx.tls.certresolver=letsencrypt" \
nginx:alpine
Acesse https://app.seudominio.com. Você verá a página padrão do Nginx com o cadeado de segurança ativo, provando que o SSL foi provisionado automaticamente.
Atualização Contínua com Watchtower
Para manter seus containers atualizados sem intervenção manual, utilizamos o Watchtower. Ele monitora um registro e atualiza serviços quando novas imagens são encontradas.
- Deploy do Watchtower no Manager:
docker service create \
--name watchtower \
--mount type=bind,source=/var/run/docker.sock,target=/var/run/docker.sock \
--label com.centurylinklabs.watchtower.enable=true \
--env WATCHTOWER_CLEANUP=true \
--env WATCHTOWER_POLL_INTERVAL=3600 \
containrrr/watchtower
O Watchtower irá verificar a cada hora (3600 segundos) se há novas versões das imagens em uso e atualizará os serviços automaticamente.
Registry Privado para Segurança
Para produção, evite usar imagens públicas do Docker Hub. Configure um registry privado para armazenar suas imagens internas.
- No Manager, execute o serviço de registry:
docker service create \
--name registry \
--publish 5000:5000 \
--constraint=node.role==manager \
--mount type=bind,source=/opt/registry/data,target=/var/lib/registry \
registry:2
Suas imagens podem agora ser enviadas para http://<IP_MANAGER>:5000/sua-app:tag.
Troubleshooting Containers e Logs
O troubleshooting containers no Swarm difere do Docker padrão, pois os contêineres podem estar em qualquer nó. Use as ferramentas de orquestração para diagnosticar problemas.
- Verificar status do serviço:
docker service ls
- Verificar tarefas e nós específicos:
docker service ps <nome_do_servico>
Este comando mostra em qual nó a tarefa está rodando e seu estado (Running, Pending, Failed).
- Acessar logs de um serviço:
docker service logs -f <nome_do_servico>
Isso agrega os logs de todas as réplicas do serviço. Se um container falhar, verifique o estado com docker inspect <container_id> para detalhes sobre erros de inicialização.
- Acessar shell em um container em execução:
docker exec -it <container_id> sh
Se precisar acessar um nó específico para debug de rede ou sistema operacional, use docker node inspect <nome_do_nodo> para obter o IP e SSH diretamente.
Escalando Horizontalmente
Uma das maiores vantagens do Swarm é a escalabilidade. Para aumentar a capacidade de resposta da sua aplicação, basta alterar o número de réplicas.
docker service scale nginx-teste=5
O Swarm distribuirá automaticamente as 5 réplicas pelos nós disponíveis (Manager e Workers), balanceando a carga. Para verificar a distribuição:
docker ps --filter "name=nginx"
Você verá que os containers estão rodando em diferentes IPs de host, garantindo redundância.
Boas Práticas e Considerações Finais
Ao gerenciar um cluster Docker Swarm em múltiplas VPS, considere os seguintes pontos críticos:
- Backup de Estado: O Swarm usa Raft para armazenar o estado do cluster. Certifique-se de que os dados sensíveis (banco de dados, uploads) estejam em volumes externos ou montados via NFS/S3, não apenas no disco local dos nós.
- Segurança de Rede: Configure firewalls para liberar apenas as portas necessárias (80, 443 e a porta do Swarm 2377 se houver comunicação externa, embora o ideal seja manter o cluster interno).
- Mutual TLS (mTLS): O Swarm utiliza mTLS por padrão para comunicação segura entre nós. Não desative isso em ambientes de produção.
- Monitoramento: Implemente ferramentas como Prometheus e Grafana para monitorar a saúde do cluster e dos contêineres.
Com esta configuração, você possui uma infraestrutura resiliente, escalável e segura. O uso combinado de Docker Swarm, Traefik e Watchtower permite que equipes pequenas mantenham ambientes de produção complexos com baixo overhead operacional.