Containers vs Máquinas Virtuais (VMs): O Básico Antes do Docker
O que Você Vai Aprender
- O que containers e máquinas virtuais (VMs) realmente virtualizam, a partir dos princípios fundamentais
- Por que containers são rápidos e leves, e por que VMs oferecem isolamento mais forte
- Como decidir qual usar antes de você tocar no Docker
Resumo Rápido
- Uma VM virtualiza hardware, e cada VM executa seu próprio kernel do SO convidado
- Um container compartilha o kernel do host e isola um processo com
namespacesecgroups - Containers vencem em velocidade e tamanho; VMs vencem em isolamento. Escolha pelo caso de uso (e eles se combinam bem)
Premissas
- Um host Linux (o modelo é o mesmo no Ubuntu ou na família RHEL)
- Containers significa containers Linux (Docker / Podman, etc.)
- VMs significa VMs baseadas em hypervisor (KVM / VirtualBox / VMware)
O que Realmente Difere Entre Containers e VMs?
Conclusão: Uma VM virtualiza um SO completo; um container isola apenas o processo de uma aplicação. Eles virtualizam camadas diferentes.
Ambos permitem executar múltiplos ambientes em uma máquina, mas eles virtualizam camadas diferentes.
| Aspecto | Máquina Virtual (VM) | Container |
|---|---|---|
| Virtualiza | Hardware (CPU/memória/NIC) | Um processo (como vê o SO) |
| Kernel | Kernel convidado próprio por VM | Compartilha o kernel do host |
| Tempo de boot | Dezenas de segundos a minutos | Milissegundos a segundos |
| Tamanho da imagem | Vários GB | Alguns MB a algumas centenas de MB |
| Overhead | Camada hypervisor adiciona custo | Quase nativo |
| Isolamento | Forte (kernels separados) | Moderado (kernel compartilhado) |
| SO diferente | Sim (ex.: Windows no Linux) | Não (mesmo kernel que o host) |
Uma VM reproduz uma máquina física inteira em software. Um container mostra a cada aplicação seu próprio "mundo" privado sobre o mesmo SO. Esse enquadramento mantém os dois distintos.
Por que Containers São Tão Leves e Rápidos?
Conclusão: Um container reutiliza o kernel do host em vez de inicializar um novo SO, então inicia rapidamente e usa pouca memória.
A leveza dos containers se resume ao compartilhamento de kernel. Onde uma VM inicializa um SO convidado completo (kernel mais processos init) toda vez, um container simplesmente inicia mais um processo no kernel do host já em execução.
O truque que faz esse processo parecer um SO independente são dois recursos do kernel Linux.
namespaces (separação)
Um namespace particiona quais recursos do SO um processo pode ver. Cada tipo isola uma visão diferente.
- PID: espaço de ID de processo (dentro do container o processo se vê como PID 1)
- mount: pontos de montagem do sistema de arquivos
- network: interfaces de rede e roteamento
- UTS: hostname
- IPC: comunicação entre processos
- user: mapeamento UID/GID
Liste os namespaces atuais do host com lsns.
$ lsns
cgroups (limites)
cgroups (grupos de controle) limitam e medem os recursos que um processo pode usar — CPU, memória, I/O e mais.
$ systemd-cgls
namespaces decidem "o que você vê"; cgroups decidem "quanto você recebe" Combine os dois para isolar um único processo de modo que ele se comporte como um SO autônomo. É isso que um container realmente é.
Como Funciona uma Máquina Virtual?
Conclusão: Um hypervisor virtualiza o hardware, e um SO convidado completo inicializa sobre ele.
Uma VM depende de um hypervisor que virtualiza hardware — CPU, memória, disco, NIC. O SO convidado inicializa como se aquele hardware fosse real.
Hypervisors vêm em dois tipos amplos.
- Tipo 1 (bare-metal): executa diretamente no hardware. KVM / Xen / VMware ESXi. A base de servidores e cloud.
- Tipo 2 (hospedado): executa sobre um SO host. VirtualBox / VMware Workstation. Bom para testes locais.
Como cada convidado executa seu próprio kernel, você pode executar Windows em um host Linux, junto a uma versão diferente do Linux. Um container, compartilhando o kernel do host, não pode fazer isso.
Qual Tem Isolamento Mais Forte (Segurança)?
Conclusão: VMs isolam mais fortemente. Containers compartilham um kernel, então uma vulnerabilidade no kernel pode afetar todos os containers.
Uma VM dá a cada convidado seu próprio kernel, então comprometer uma VM não vaza diretamente para outras ou para o host. O limite fica no nível de virtualização de hardware.
Um container compartilha o kernel do host. O lado negativo de ser leve é que uma vulnerabilidade no kernel deixa o risco teórico de um "container breakout" do container para o host.
Um container não é uma "VM leve." O nível de isolamento difere, então quando uma separação forte é requisito, use uma VM — ou combine VMs e containers.
Na prática, o padrão comum em cloud é executar containers dentro de uma VM: a VM fornece um limite forte, enquanto os containers dentro dela mantêm sua leveza e portabilidade.
Qual Você Deve Usar?
Conclusão: Containers para empacotamento, distribuição e densidade; VMs para um SO diferente, isolamento forte ou testes em nível de kernel.
Um guia aproximado por objetivo:
| O que você quer fazer | Melhor escolha |
|---|---|
| Empacotar e distribuir uma aplicação com seu ambiente | Container |
| Microsserviços / CI/CD | Container |
| Empacotar muitos ambientes densamente em um host | Container |
| Executar um SO diferente (ex.: Windows no Linux) | VM |
| Isolamento forte / limite multi-tenant | VM |
| Testar módulos do kernel ou o próprio SO | VM |
Quando em dúvida, pergunte:
- O kernel do host é suficiente? Se sim, um container é o primeiro candidato.
- Você precisa de um SO diferente ou kernel customizado? Se sim, use uma VM.
- Quão estrito é o requisito de isolamento? Quanto mais estrito, mais uma VM (ou containers dentro de uma VM) é adequada.
O que Saber Antes de Aprender Docker
Conclusão: O Docker envolve namespaces e cgroups em uma ferramenta amigável. Conhecendo a mecânica, seus comandos se leem como lógica, não mágica.
Quando você começar com Docker encontrará duas palavras: image e container. Mapeá-las para a mecânica acima previne confusão.
- Image: o "blueprint" para um container — um template somente-leitura agrupando a aplicação e suas dependências
- Container: um "processo em execução" iniciado a partir de uma image — realmente um processo Linux isolado por namespaces e cgroups
Então o Docker é apenas uma ferramenta que envolve os recursos do kernel que você viu aqui em uma forma amigável para humanos. Abandone o equívoco "container = VM ultra-leve" e os comandos do Docker começam a fazer sentido naturalmente.
Esse nível de compreensão é suficiente "Compartilha o kernel, separado por namespaces, limitado por cgroups" — mantenha essa linha em mente e a introdução ao Docker vai tranquilamente.