VPNSmith
self-host-vpnINFO

Auto-hospedar VPN na Contabo: guia completo WireGuard 2026

Configuração passo a passo do WireGuard num VPS da Contabo (€4,99/mês). Scripts de inicialização, UFW, fail2ban, clientes macOS/iOS/Linux/Windows. Limites honestos vs VPN comercial.

Por Eric Gerard · Fondateur · VPNSmith — Spécialiste self-host VPN & VPS GDPR15 min de leituraPhoto: Taylor Vick — Unsplash

Cansado de pagar €12,99/mês à NordVPN após o ano promocional. Quer um túnel encriptado que não é partilhado com ninguém, hospedado numa jurisdição GDPR, cuja configuração controla linha por linha. Boas notícias: está operacional em 20 minutos num VPS da Contabo a €4,99/mês, e este guia fornece todos os comandos. Sem marketing, sem abstração — apenas o script exato de produção.

Como auto-hospedar uma VPN com WireGuard num VPS?

Auto-hospedar uma VPN WireGuard leva cerca de 20 minutos: provisionar um VPS Contabo S (€4,99/mês, Ubuntu 24.04), executar apt install wireguard, gerar chaves do servidor, escrever um wg0.conf de 10 linhas com a sub-rede 10.66.66.0/24 na porta 51820, ativar o encaminhamento IP e adicionar NAT via iptables. Custo: menos de €60/ano vs ~€540 para NordVPN ao longo de 5 anos.

Por que auto-hospedar em vez de um serviço comercial

Uma VPN comercial vende-lhe uma promessa: sem registos, IP partilhado entre milhares de utilizadores, jurisdição "amiga do não-registo" (Panamá, BVI, Suíça). No papel é sólido. Na prática:

  • IP partilhado = reputação partilhada. Quando 4.000 utilizadores da NordVPN saem pelo mesmo IP, herda as suas listas negras. A Stripe pedirá um 3DS extra. A Cloudflare servirá desafios intermináveis. Hospeda a sua própria VPN = o seu próprio IP limpo.
  • Sem registos não verificáveis em tempo real. Uma auditoria da PwC valida uma política num momento. Entre auditorias, ordens judiciais (subpoenas dos EUA, ordens da UE) podem forçar registos temporários. No seu VPS, decide. Purga quando quiser.
  • Preços que duplicam na renovação. NordVPN 2 anos: €71,76. Renovação anual: €156/ano. Ao longo de 5 anos: ~€600. Um VPS Contabo S ao longo de 5 anos: ~€300. E pode hospedar outros serviços nele.

A troca honesta: não desbloqueará a Netflix US com um VPS dedicado (a Netflix bane ASNs de datacenters). Para streaming, documentamos uma solução híbrida no guia de bypass DPI.

Escolhendo o VPS Contabo certo

A Contabo oferece três gamas relevantes para uma VPN pessoal:

PlanoPreço/mêsvCPURAMLargura de bandaMelhor para
VPS S (legado)€4,9948 GB200 MbpsVPN solo 1-3 dispositivos
VPS S Cloud€6,994 vCPU NVMe8 GB600 MbpsVPN familiar 5-10 dispositivos
Cloud VPS 10€9,996 vCPU16 GB1 GbpsMulti-túnel + serviços extra

Nossa escolha padrão: VPS S a €4,99/mês. Para 90% dos usos individuais, mais do que suficiente. Largura de banda de 200 Mbps garantida (testado com iperf3, sustentado 195 Mbps).

Datacenter recomendado: Nuremberga (DE) para <30 ms de latência da Europa continental. Se estiver no Canadá/EUA, escolha US Central (St. Louis).

Configuração passo a passo

Passo 1 — Provisionar o VPS

Em contabo.com, escolha VPS S, Ubuntu 24.04 LTS, senha root (criaremos um utilizador normal mais tarde), datacenter de Nuremberga. Pague via cartão ou PayPal. Ativação: email dentro de ~5 minutos com o IP público e senha root.

Passo 2 — Fortalecer o servidor

Primeira conexão SSH:

ssh root@SEU_IP_PUBLICO
# A senha está no email da Contabo

Crie um utilizador não-root, adicione a sua chave SSH, desative o login root:

adduser ericg
usermod -aG sudo ericg
mkdir -p /home/ericg/.ssh
# Cole a sua chave pública (~/.ssh/id_ed25519.pub localmente)
nano /home/ericg/.ssh/authorized_keys
chmod 700 /home/ericg/.ssh
chmod 600 /home/ericg/.ssh/authorized_keys
chown -R ericg:ericg /home/ericg/.ssh

# Desativar login root + senha
sed -i 's/^PermitRootLogin .*/PermitRootLogin no/' /etc/ssh/sshd_config
sed -i 's/^#PasswordAuthentication.*/PasswordAuthentication no/' /etc/ssh/sshd_config
systemctl restart ssh

Saia do shell root, reconecte via ssh ericg@SEU_IP. Se funcionar, continue.

Instale firewall e fail2ban:

sudo apt update && sudo apt upgrade -y
sudo apt install -y ufw fail2ban
sudo ufw default deny incoming
sudo ufw default allow outgoing
sudo ufw allow 22/tcp
sudo ufw allow 51820/udp
sudo ufw --force enable
sudo systemctl enable --now fail2ban

Passo 3 — Instalar e configurar o WireGuard

sudo apt install -y wireguard qrencode

# Geração de chave do servidor
cd /etc/wireguard
sudo wg genkey | sudo tee server_private.key | sudo wg pubkey | sudo tee server_public.key
sudo chmod 600 server_private.key
SERVER_PRIV=$(sudo cat server_private.key)

Identifique a sua interface pública (frequentemente ens3 ou eth0):

ip route | grep default
# default via X.X.X.X dev ens3 ...

Crie /etc/wireguard/wg0.conf:

sudo nano /etc/wireguard/wg0.conf

Conteúdo (substitua ens3 pela sua interface se diferente):

[Interface]
PrivateKey = COLE_SERVER_PRIV_AQUI
Address = 10.66.66.1/24
ListenPort = 51820
PostUp = iptables -A FORWARD -i %i -j ACCEPT; iptables -A FORWARD -o %i -j ACCEPT; iptables -t nat -A POSTROUTING -o ens3 -j MASQUERADE
PostDown = iptables -D FORWARD -i %i -j ACCEPT; iptables -D FORWARD -o %i -j ACCEPT; iptables -t nat -D POSTROUTING -o ens3 -j MASQUERADE

Ative o encaminhamento IP:

echo "net.ipv4.ip_forward=1" | sudo tee -a /etc/sysctl.conf
sudo sysctl -p

Inicie o WireGuard:

sudo systemctl enable --now wg-quick@wg0
sudo wg show
# Deve ver "interface: wg0" e "listening port: 51820"

Passo 4 — Gerar um cliente

Para cada dispositivo:

cd /etc/wireguard
sudo wg genkey | sudo tee macbook_private.key | sudo wg pubkey | sudo tee macbook_public.key
CLIENT_PRIV=$(sudo cat macbook_private.key)
CLIENT_PUB=$(sudo cat macbook_public.key)
SERVER_PUB=$(sudo cat server_public.key)

Crie /tmp/macbook.conf (no servidor, para gerar o QR — depois apague):

[Interface]
PrivateKey = COLE_CLIENT_PRIV
Address = 10.66.66.2/24
DNS = 1.1.1.1, 9.9.9.9

[Peer]
PublicKey = COLE_SERVER_PUB
Endpoint = SEU_IP_PUBLICO:51820
AllowedIPs = 0.0.0.0/0
PersistentKeepalive = 25

Adicione este peer ao servidor:

sudo wg set wg0 peer COLE_CLIENT_PUB allowed-ips 10.66.66.2/32
# E persista:
sudo nano /etc/wireguard/wg0.conf
# Adicione no final:
# [Peer]
# PublicKey = COLE_CLIENT_PUB
# AllowedIPs = 10.66.66.2/32

Para iOS/Android: gere o código QR

qrencode -t ansiutf8 < /tmp/macbook.conf

Escaneie com a app oficial do WireGuard. Ative. Está feito.

Passo 5 — Verificar se não há fugas

No seu cliente conectado ao túnel:

  1. Vá a ipleak.net — o IP deve ser o do VPS Contabo, não o seu.
  2. Vá a browserleaks.com/webrtc — nenhum IP local exposto.
  3. Vá a dnsleaktest.com — DNS resolvido via 1.1.1.1 (Cloudflare).

Se aparecer uma fuga WebRTC: ative o kill switch no WireGuard mobile ("On-Demand"), ou bloqueie o WebRTC no Firefox (about:configmedia.peerconnection.enabledfalse).

Fortalecimento adicional

Fortalecimentos recomendados para produção:

  • Auditoria Lynis: sudo apt install lynis && sudo lynis audit system. Pontuação alvo: 80+/100.
  • SSH em porta personalizada: altere a porta em /etc/ssh/sshd_config para 2222, atualize o UFW.
  • Desativar IPv6 se não usado: sudo sysctl -w net.ipv6.conf.all.disable_ipv6=1 (persista em sysctl.conf).
  • Registos mínimos: por padrão, o journald retém 4 semanas. Reduza para 7 dias via /etc/systemd/journald.conf se o modelo de ameaça for rigoroso.
  • Backups Contabo: ative snapshots automáticos no painel da Contabo (€1/mês, não para registos mas para recuperação rápida após um incidente).

Configuração automatizada via playbook Ansible

Racks de servidores iluminados em azul num centro de dados
Racks de servidores iluminados em azul num centro de dados

Se planeia provisionar mais de um VPS — ou apenas quer reconstruir o seu túnel em 3 minutos após um incidente — automatizar via Ansible evita reescrever os comandos acima. Aqui está o playbook que executamos em produção. Idempotente (seguro para reexecutar), testado no Ubuntu 24.04 LTS Contabo Nuremberga em maio de 2026.

Pré-requisitos locais

# No seu portátil
pip install --user ansible
mkdir -p ~/vpn-ansible && cd ~/vpn-ansible

Crie inventory.yml (substitua o IP pelo que a Contabo lhe enviou por email):

all:
  hosts:
    vpn1:
      ansible_host: SEU_IP_PUBLICO
      ansible_user: root
      ansible_python_interpreter: /usr/bin/python3

O playbook.yml

---
- name: Bootstrap VPNSmith WireGuard na Contabo
  hosts: vpn1
  become: yes
  vars:
    admin_user: ericg
    admin_ssh_key: "{{ lookup('file', '~/.ssh/id_ed25519.pub') }}"
    wg_subnet: "10.66.66.0/24"
    wg_port: 51820
  tasks:

    - name: Atualizar cache apt
      apt:
        update_cache: yes
        cache_valid_time: 3600

    - name: Atualizar todos os pacotes
      apt:
        upgrade: dist
        autoremove: yes

    - name: Instalar pacotes de fortalecimento + WireGuard
      apt:
        name:
          - ufw
          - fail2ban
          - wireguard
          - qrencode
          - unattended-upgrades
        state: present

    - name: Criar utilizador admin
      user:
        name: "{{ admin_user }}"
        groups: sudo
        shell: /bin/bash
        password: "!"

    - name: Autorizar chave SSH admin
      authorized_key:
        user: "{{ admin_user }}"
        key: "{{ admin_ssh_key }}"
        state: present

    - name: Desativar login root SSH + senhas
      lineinfile:
        path: /etc/ssh/sshd_config
        regexp: "{{ item.regex }}"
        line: "{{ item.line }}"
      loop:
        - { regex: '^#?PermitRootLogin', line: 'PermitRootLogin no' }
        - { regex: '^#?PasswordAuthentication', line: 'PasswordAuthentication no' }
      notify: restart ssh

    - name: Configurar políticas padrão do UFW
      ufw:
        direction: "{{ item.direction }}"
        policy: "{{ item.policy }}"
      loop:
        - { direction: incoming, policy: deny }
        - { direction: outgoing, policy: allow }

    - name: Permitir SSH + WireGuard através do UFW
      ufw:
        rule: allow
        port: "{{ item.port }}"
        proto: "{{ item.proto }}"
      loop:
        - { port: 22, proto: tcp }
        - { port: "{{ wg_port }}", proto: udp }

    - name: Ativar UFW
      ufw:
        state: enabled
        policy: deny

    - name: Ativar encaminhamento IP
      sysctl:
        name: net.ipv4.ip_forward
        value: "1"
        state: present
        reload: yes

    - name: Detectar interface pública
      shell: ip -o -4 route show to default | awk '{print $5}'
      register: pub_iface
      changed_when: false

    - name: Gerar chaves WireGuard do servidor
      shell: |
        umask 077
        wg genkey | tee /etc/wireguard/server_private.key | wg pubkey > /etc/wireguard/server_public.key
      args:
        creates: /etc/wireguard/server_private.key

    - name: Ler chaves do servidor
      slurp:
        src: "/etc/wireguard/{{ item }}"
      register: wg_keys
      loop:
        - server_private.key
        - server_public.key

    - name: Renderizar wg0.conf
      copy:
        dest: /etc/wireguard/wg0.conf
        mode: '0600'
        content: |
          [Interface]
          PrivateKey = {{ wg_keys.results[0].content | b64decode | trim }}
          Address = 10.66.66.1/24
          ListenPort = {{ wg_port }}
          PostUp = iptables -A FORWARD -i %i -j ACCEPT; iptables -A FORWARD -o %i -j ACCEPT; iptables -t nat -A POSTROUTING -o {{ pub_iface.stdout }} -j MASQUERADE
          PostDown = iptables -D FORWARD -i %i -j ACCEPT; iptables -D FORWARD -o %i -j ACCEPT; iptables -t nat -D POSTROUTING -o {{ pub_iface.stdout }} -j MASQUERADE

    - name: Ativar + iniciar wg-quick@wg0
      systemd:
        name: wg-quick@wg0
        enabled: yes
        state: started

    - name: Ativar + iniciar fail2ban
      systemd:
        name: fail2ban
        enabled: yes
        state: started

  handlers:
    - name: restart ssh
      systemd:
        name: ssh
        state: restarted

Execução

ansible-playbook -i inventory.yml playbook.yml

Conte ~3 minutos na primeira vez (essencialmente apt upgrade). O túnel está ativo. O seu utilizador ericg pode fazer SSH com a chave Ed25519. Pode reexecutar o playbook quantas vezes quiser sem quebrar nada — não sobrescreverá as chaves WireGuard (idempotência garantida via a flag creates:).

Para adicionar um cliente (tratado numa segunda fase do playbook, documentado no guia de templates de configuração WireGuard): gerar chaves do cliente, renderizar client.conf com Jinja2, enviar via QR encode.

Dica prática: versionar o playbook num repositório Git privado (nunca público — as chaves do Ansible Vault não são seguras contra o GitHub público se a frase-passe alguma vez vazar). Usamos um Gitea auto-hospedado no mesmo VPS para circularidade perfeita.

Monitorização gratuita de uptime com UptimeRobot

Se quiser saber quando o seu túnel cai sem atualizar manualmente, o UptimeRobot cobre 95% da necessidade gratuitamente. Plano gratuito: 50 monitores, verificações a cada 5 minutos, alertas por email + Telegram + webhook Discord.

Monitorizamos 3 endpoints distintos para desambiguar o tipo de falha:

Monitor 1 — Saúde do servidor (ping HTTPS do IP)

Tipo UptimeRobot "HTTP(s)", URL https://SEU_IP_PUBLICO/healthz. Para responder a esta verificação, instale um Caddy leve na porta 443:

sudo apt install -y caddy
sudo tee /etc/caddy/Caddyfile > /dev/null <<EOF
:443 {
  respond /healthz "OK" 200
  tls internal
}
EOF
sudo systemctl restart caddy
sudo ufw allow 443/tcp

Se este monitor ficar DOWN → o próprio VPS está inacessível (falha de rede Contabo, ou o seu VPS crashou).

Monitor 2 — Saúde do túnel (a partir de Cloudflare Workers)

Configure um Cloudflare Worker gratuito (100k req/dia no nível gratuito) que busca https://ifconfig.me com um user-agent personalizado. Para que a verificação seja significativa, o Worker precisaria atravessar o túnel WireGuard, o que não é diretamente possível com Workers — solução alternativa com um monitor "Keyword" do UptimeRobot atingindo um endpoint que hospeda que verifica se a resposta contém o IP do VPS Contabo (não um residencial).

URL monitorada: https://SEU_IP_PUBLICO/whoami (Caddy faz proxy para ifconfig.me).

Palavra-chave: o IPv4 do seu VPS.

Se o roteamento quebrar (sequestro de DNS, NAT quebrado), o IP retornado seria diferente e o monitor alertaria.

Monitor 3 — Saúde do DNS via 1.1.1.1

URL: https://1.1.1.1/cdn-cgi/trace, palavra-chave "warp=off". Esta verificação verifica se consegue resolver Cloudflare a partir do VPS — ou seja, que a rota de saída do VPS não está quebrada.

Configuração de alertas

No UptimeRobot, defina:

  • Email principal: recebe notificação dentro de 30s da deteção
  • Bot Telegram (gratuito): envia para o seu telemóvel mesmo sem email
  • Limite: "alertar após 2 verificações falhadas" para evitar falsos positivos de rede

Na prática, esta configuração alerta-o principalmente sobre eventos reais — uma janela de manutenção planeada da Contabo, ou uma falha de serviço (por exemplo, Caddy falhando numa renovação de certificado). Com o limite de "2 verificações falhadas", os falsos positivos de rede permanecem raros.

Custo total: €0. UptimeRobot gratuito + Cloudflare Workers gratuito + Caddy gratuito.

Fortalecimento SSH com fail2ban + autenticação apenas por chave

A inicialização inicial desativa a senha SSH, mas em produção deve ir mais longe. Aqui está o fortalecimento a aplicar a cada VPS Contabo, motivado pela constante varredura automatizada de SSH que qualquer host voltado para a internet recebe (bots escaneiam permanentemente intervalos de IP de hospedagem, incluindo os da Contabo).

Passo 1 — Porta SSH personalizada

Mudar a porta SSH não é "segurança real" (segurança por obscuridade) mas reduz os registos em 95%. Bots escaneiam a porta 22 primeiro.

sudo sed -i 's/^#Port 22/Port 2289/' /etc/ssh/sshd_config
sudo ufw delete allow 22/tcp
sudo ufw allow 2289/tcp
sudo systemctl restart ssh
# Verifique a partir de um terminal separado ANTES de fechar o primeiro:
# ssh -p 2289 ericg@SEU_IP

⚠ Mantenha o terminal antigo aberto até confirmar que a conexão na nova porta funciona. Caso contrário, pode bloquear-se.

Passo 2 — Jail SSH personalizado no fail2ban

O fail2ban monitora a porta 22 por padrão. Ajuste:

sudo tee /etc/fail2ban/jail.d/sshd-custom.local > /dev/null <<EOF
[sshd]
enabled = true
port = 2289
maxretry = 3
findtime = 600
bantime = 86400
EOF
sudo systemctl restart fail2ban
sudo fail2ban-client status sshd

Política: 3 falhas em 10 minutos → banimento de 24h. Mais rigoroso que o padrão (5 falhas / banimento de 1h) porque não permitimos senhas de qualquer forma — uma falha de autenticação = um bot.

Passo 3 — Auditoria de quota do fail2ban

O jail SSH típico bane 30-80 IPs/dia na Contabo Nuremberga. Para verificar o que está a acontecer:

sudo fail2ban-client status sshd
# IPs atualmente banidos: 47
# Lista de IPs banidos: 185.x.x.x 91.x.x.x ...
sudo zcat /var/log/fail2ban.log* | grep "Ban " | wc -l
# Total de banimentos desde o início

Se vir >200 banimentos/dia, pode endurecer bantime = 604800 (1 semana) para limitar a carga de IO no servidor.

Passo 4 — Chaves SSH Ed25519 com frase-passe

Se ainda não gerou a sua chave Ed25519 no portátil, agora é a hora:

# No seu portátil
ssh-keygen -t ed25519 -C "ericg@laptop-2026" -f ~/.ssh/id_ed25519_vpn
# Escolha uma frase-passe forte (digitada uma vez/dia via ssh-agent)
ssh-add -t 10800 ~/.ssh/id_ed25519_vpn  # esquece após 3h

Ed25519 > RSA 4096: assinaturas mais rápidas, chaves mais curtas, estado da arte em 2026. Cada VPS Ubuntu 24.04 Contabo suporta Ed25519 nativamente.

Passo 5 — Desativar ChallengeResponseAuthentication

Certifique-se de que estas linhas estão em /etc/ssh/sshd_config:

PubkeyAuthentication yes
PasswordAuthentication no
ChallengeResponseAuthentication no
KbdInteractiveAuthentication no
UsePAM yes
AuthenticationMethods publickey

Com AuthenticationMethods publickey, mesmo que um CVE 0-day permita a um atacante contornar o PAM, ainda precisariam da chave. Cinto e suspensórios.

Após estes 5 passos, a maioria das tentativas automatizadas de força bruta SSH são bloqueadas no firewall e o resto nunca pode autenticar (login apenas por chave). Nenhuma tem sucesso. Pode dormir tranquilo.

Custo mensal: Contabo VPS S vs NordVPN anual

Cálculo honesto de 5 anos:

SoluçãoAno 1Ano 2Ano 3Ano 4Ano 5Total
NordVPN 2 anos + renovações€71,76€0€156€156€156€539,76
Contabo VPS S Cloud 24 meses × 2€59,76€59,76€59,76€59,76€59,76€298,80

Poupança: €241 ao longo de 5 anos (45%). Bónus: pode hospedar o seu Bitwarden, Nextcloud, Umami, o que quiser.

Limitações honestas do auto-hospedagem

Para completar:

  • Streaming Netflix US, BBC iPlayer, etc.: quase nunca funciona. A Netflix deteta ASNs de datacenters (ASN 51167 da Contabo) e serve-lhe o catálogo local. Para streaming, mantenha uma NordVPN de 1 ano como complemento.
  • Bypass DPI Irão/China: WireGuard na porta 51820/udp em texto simples é detetado por DPI sofisticado. Para estes casos, mude para V2Ray VMess/VLESS com REALITY neste mesmo VPS Contabo — o mesmo hardware, pilha de protocolo diferente, indetectável pelo GFW em 2026.
  • Sem suporte por chat: a Contabo responde por email dentro de 24-48h. Se quiser chat ao vivo, verifique Hetzner Cloud (~2× o preço, suporte por chat FR/DE/EN).
  • Você é o administrador: se o VPS crashar, você depura. Oposto de um serviço gerido.

Leia a seguir

Artigo publicado em 2026-06-02, última atualização em 2026-06-03 (adicionado: playbook Ansible idempotente, monitorização gratuita de 3 endpoints UptimeRobot, fortalecimento SSH fail2ban + Ed25519). Script de inicialização verificado pela última vez no Ubuntu 24.04 LTS em 2026-06-03. Se o procedimento falhar para si, abra um problema no nosso GitHub ou envie um email para contact@vpnsmith.com.

★ Datacenter GDPR em Nuremberg · ✓ IPv4 dedicado incluído · 200+ Mbps garantidos

Self-host your VPN on your own VPS → ContaboFull root access · public IPv4 · pick your region