Modelagem de ameaças tem fama de coisa cara. Metodologia com sigla, planilha de trinta abas, consultor. Time pequeno olha aquilo, conclui que não é pra ele e segue construindo no escuro.
A versão que cabe num time de cinco pessoas leva uma hora e usa um quadro branco. Não é a versão completa. É a versão que muda decisão, que é o que importa.
Antes de começar
Junte quem escreve o código, não quem gerencia. Duas a cinco pessoas. Uma feature específica na mesa, não “o sistema”. Se a pauta for o sistema inteiro, a conversa vira genérica e não sai decisão.
Boas pautas: o novo fluxo de convite de usuário, a integração com o parceiro X, o upload de documento, a API pública que vai abrir.
Passo 1: desenhe o caminho do dado (15 minutos)
Não é diagrama de arquitetura. É o percurso.
De onde vem o dado, por onde passa, onde para. Navegador, seu API, fila, banco, terceiro. Desenhe feio.
Depois marque as fronteiras: cada lugar onde o dado troca de dono ou de nível de confiança. Do navegador pro seu servidor é uma fronteira. Do seu servidor pro gateway de pagamento é outra. Da fila pro worker é outra.
Fronteira é onde mora quase todo problema, porque é onde alguém assume que a etapa anterior já validou.
Passo 2: quatro perguntas por fronteira (25 minutos)
Em cada seta do desenho:
Quem pode mandar coisa por aqui? A resposta honesta costuma ser mais gente do que o time imaginava. “Só o nosso frontend” quase nunca é verdade, porque o endpoint está na internet e o frontend é código que roda na máquina de outra pessoa.
O que acontece se o conteúdo for hostil? Não malformado: hostil. ID de outro tenant, valor negativo, array com cem mil itens, string de dez megabytes.
O que acontece se a mensagem chegar duas vezes? Ou fora de ordem, ou com três dias de atraso. Fila entrega de novo. Webhook reenvia. Cliente clica duas vezes.
Como a gente descobriria que deu errado? Essa é a mais importante e a que mais deixa silêncio na sala.
Anote cada resposta ruim num post-it. Não discuta a solução ainda, senão a conversa trava no primeiro item e vocês só cobrem um terço do desenho.
Passo 3: separe em três pilhas (10 minutos)
Agora sim. Cada post-it vai pra uma pilha:
Consertar agora, porque é barato ou é grave. Escrever no backlog com dono e prazo, porque é real mas dá pra planejar. Aceitar conscientemente, com a razão escrita.
A terceira pilha é a que dá maturidade ao processo. Time que não aceita risco nenhum acaba não fazendo modelagem de ameaça nunca mais, porque virou fonte de trabalho infinito. Escrever “aceitamos que o parceiro X vê o volume agregado, porque está em contrato” é um resultado legítimo.
Passo 4: transforme em teste (10 minutos)
Essa parte quase todo mundo pula, e é a que faz o exercício valer daqui a um ano.
Para cada item da primeira pilha, escreva um teste automatizado. Não um documento: um teste.
it("não deixa usuário de outra organização ler o diagnóstico", async () => {
const { token } = await loginAs(userFromOrgB);
const res = await request(app)
.get(`/diagnostics/${diagnosticFromOrgA.id}`)
.set("Authorization", `Bearer ${token}`);
expect(res.status).toBe(404); // 404, não 403: não confirma existência
});
Documento envelhece calado. Teste quebra e avisa.
Detalhe que vale a pena: responder 404 em vez de 403 evita confirmar que aquele recurso existe. Diferença pequena que atrapalha bastante quem está sondando.
O que costuma aparecer
Depois de fazer isso algumas vezes, a lista de achados fica repetitiva. E isso é ótimo, porque significa que dá pra antecipar.
Endpoint que confere quem é o usuário e esquece de conferir se o recurso é dele. É o campeão absoluto.
Worker que confia no conteúdo da fila porque “só a gente publica ali”.
Webhook sem validação de assinatura, aceitando qualquer POST que tenha o formato certo.
Endpoint de exportação sem limite, que qualquer um usa pra puxar a base inteira.
Log que grava o corpo da requisição em produção.
Se você olhar essa lista e reconhecer três coisas do seu sistema, a hora já se pagou.
Quando repetir
Não é ritual mensal. É gatilho: toda vez que entra uma fronteira nova. Integração nova, endpoint público novo, tipo de dado novo, parceiro novo.
Uma hora por fronteira nova é barato perto do custo de descobrir depois. E, diferente de quase toda prática de segurança, essa não exige nenhuma ferramenta nem ninguém com cargo especializado.
Escrevi sobre o resto do básico em como construir aplicações seguras.