Força bruta: tentando senha até acertar — e como travar isso
Sem limite nenhum, adivinhar senha vira só uma questão de quantas tentativas por segundo o atacante consegue automatizar.
Ataque de força bruta contra login não tem nada de sofisticado: um script tenta login repetidamente, trocando a senha a cada tentativa, até uma bater. O que separa um login vulnerável de um protegido não é a força da senha da vítima — é se o servidor deixa esse script tentar milhares de vezes por minuto sem nenhuma consequência.
O ataque, sem limite nenhum
Clique em “Reproduzir fluxo” para ver a requisição passo a passo.
Sem defesa nenhuma, o único obstáculo do atacante é o tempo de rede — e listas de senhas comuns (as milhares de senhas mais usadas do mundo, já compiladas publicamente) fazem esse ataque funcionar contra uma fração significativa de contas reais, não só contra senhas exóticas de propósito.
Bloqueio após N tentativas
A defesa mais direta: contar tentativas malsucedidas por conta (ou por IP, ou os dois combinados) e recusar novas tentativas depois de um limite, por um período.
tentativas_falhas["ana@exemplo.com"] += 1 // a cada login incorreto
se tentativas_falhas["ana@exemplo.com"] >= 5:
bloquear_login("ana@exemplo.com", por: 15.minutos)
responder(429, "Muitas tentativas. Tente novamente mais tarde.")Bloquear por conta (o email tentado) impede um atacante mirando um alvo específico, mesmo que ele troque de IP a cada tentativa. Bloquear por IP impede um atacante testando muitas contas diferentes a partir da mesma origem. Um sistema robusto normalmente combina os dois, porque cada um cobre um padrão de ataque que o outro sozinho deixaria passar.
Delay progressivo — uma alternativa mais suave que bloqueio total
Bloqueio total tem um efeito colateral incômodo: um usuário legítimo que errou a senha 5 vezes seguidas fica impedido de tentar de novo, mesmo lembrando a senha certa na sexta tentativa. Uma alternativa (ou complemento) é o delay progressivo: cada tentativa falha subsequente espera um pouco mais antes de responder, sem bloquear completamente.
tentativa 1 falhou → responde imediatamente
tentativa 2 falhou → espera 1s antes de responder
tentativa 3 falhou → espera 2s
tentativa 4 falhou → espera 4s
tentativa 5 falhou → espera 8s
// dobrando a cada tentativa, o tempo pra testar 100 senhas passa de
// segundos pra horas, sem nunca bloquear alguém completamenteCAPTCHA — o último recurso, não o primeiro
CAPTCHA (aquele desafio "eu não sou um robô") funciona, mas piora a experiência de todo usuário legítimo pra se defender de um problema que afeta só uma fração de tentativas. Por isso, a prática comum é aplicar CAPTCHA só depois de algumas tentativas falhas seguidas (ou em conjunto com bloqueio/delay), não em todo login desde a primeira tentativa — reservando o atrito extra pra quando já existe sinal concreto de comportamento suspeito.
Exercício
Um sistema bloqueia uma conta por 15 minutos após 5 tentativas falhas de login. Um atacante percebe isso e passa a tentar senhas contra centenas de contas diferentes, uma tentativa por conta (nunca chegando a 5 na mesma conta). O bloqueio por conta continua sendo suficiente sozinho? O que complementaria essa defesa?