Depure relatórios de bugs que você não escreveu com um fluxo prático para reproduzir problemas, isolar UI/API/banco de dados e solicitar uma correção mínima e testável.

Depurar um relatório de bug que você não escreveu é mais difícil porque falta o mapa mental do autor. Você não sabe o que é frágil, o que é “normal” ou quais atalhos foram tomados. Um sintoma pequeno (um botão, um erro de digitação, uma tela lenta) pode vir de um problema mais profundo na API, no banco de dados ou em um job em background.
Um relatório útil te dá quatro coisas:
A maioria dos relatos só dá o último: “Salvar não funciona”, “está quebrado”, “erro aleatório”. Falta o contexto que torna o problema repetível: papel do usuário, registro específico, ambiente (prod vs staging) e se começou após alguma mudança.
O objetivo é transformar um sintoma vago em uma reprodução confiável. Uma vez que você consiga fazê-lo acontecer sob demanda, deixa de ser um mistério. É uma sequência de checagens.
O que você pode controlar de imediato:
“Pronto” não é “acho que consertei”. Pronto é: seus passos de reprodução passam após uma pequena mudança, e você retesta rapidamente comportamentos próximos que poderia ter afetado.
A maneira mais rápida de perder tempo é mudar várias coisas ao mesmo tempo. Congele seu ponto de partida para que cada resultado de teste signifique algo.
Escolha um ambiente e se mantenha nele até conseguir reproduzir o problema. Se o relato veio de produção, confirme lá primeiro. Se for arriscado, use staging. Local é ok se você conseguir reproduzir de perto os dados e configurações.
Depois, identifique qual código está realmente rodando: versão, data do build e quaisquer feature flags ou configs que afetem o fluxo. Pequenas diferenças (integrações desabilitadas, URL base da API diferente, jobs em background ausentes) podem transformar um bug real em um fantasma.
Crie um setup de teste limpo e repetível. Use uma conta nova e dados conhecidos. Se puder, resete o estado antes de cada tentativa (logout, limpar cache, começar do mesmo registro).
Anote suposições conforme avança. Isso não é trabalho inútil; evita que você discuta consigo mesmo depois.
Um template de nota de baseline:
Se a reprodução falhar, essas notas dizem o que variar a seguir, um botão de cada vez.
A vitória mais rápida é transformar uma reclamação vaga em algo que você pode rodar como um script.
Comece reescrevendo o relato como uma curta user story: quem faz o quê, onde e o que esperava. Depois adicione o resultado observado.
Exemplo de reescrita:
"Como administrador de cobrança, quando eu mudo o status de uma fatura para Pago e clico em Salvar na página da fatura, o status deve persistir. Em vez disso, a página permanece igual e o status não muda após o refresh."
Em seguida, capture as condições que tornam o relato verdadeiro. Bugs frequentemente dependem de um detalhe único: papel, estado do registro, localidade ou ambiente.
Entradas-chave para anotar antes de começar a clicar:
Colete evidências enquanto ainda tiver o comportamento original. Capturas de tela ajudam, mas uma gravação curta é melhor porque captura timing e cliques exatos. Sempre anote um timestamp (incluindo fuso horário) para cruzar com os logs depois.
Três perguntas esclarecedoras que removem a maior parte das suposições:
Não comece chutando a causa. Faça o problema acontecer de propósito, da mesma forma, mais de uma vez.
Primeiro, siga os passos do repórter exatamente como escritos. Não “melhore” eles. Note o primeiro ponto onde sua experiência diverge, mesmo que pareça pequeno (label de botão diferente, campo faltando, texto de erro ligeiramente distinto). Essa primeira diferença é muitas vezes a pista.
Um fluxo simples que funciona na maioria das aplicações:
Depois que for repetível, varie uma coisa por vez. Testes de variável única que normalmente valem a pena:
Termine com um curto script de repro que outra pessoa possa executar em 2 minutos: estado inicial, passos, entradas e a primeira observação falha.
Antes de ler todo o código, decida qual camada está falhando.
Pergunte: o sintoma está apenas na UI, ou os dados e respostas da API também estão errados?
Exemplo: “Meu nome de perfil não atualizou.” Se a API retorna o nome novo mas a UI ainda mostra o antigo, suspeite de estado/caching na UI. Se a API nunca salvou, você provavelmente está em território de API ou BD.
Perguntas rápidas de triagem que você pode responder em minutos:
Checagens de UI são sobre visibilidade: erros no console, aba Network e estado obsoleto (UI não refaz fetch após salvar, ou lê de um cache antigo).
Checagens de API são sobre contrato: payload (campos, tipos, IDs), código de status e corpo de erro. Um 200 com um body surpreendente pode importar tanto quanto um 400.
Checagens de BD são sobre realidade: linhas faltando, gravações parciais, violação de constraints, updates que afetam zero linhas porque o WHERE não bate.
Para se orientar, desenhe um pequeno mapa: qual ação da UI dispara qual endpoint e quais tabelas ele lê ou escreve.
A clareza frequentemente vem de seguir uma requisição real do clique até o banco e de volta.
Capture três âncoras do relato ou do seu repro:
Se não tiver correlation ID, adicione um no gateway/backend e inclua-o nos cabeçalhos de resposta e nos logs.
Para não se afogar em ruído, capture apenas o necessário para responder “Onde falhou e por quê?”:
Sinais para observar:
Se “funcionou ontem” mas não hoje, suspeite de drift no ambiente: flags alteradas, segredos rotacionados, migrations faltando ou jobs que pararam de rodar.
O bug mais fácil de consertar é um experimento pequeno e repetível.
Reduza tudo: menos cliques, menos campos, o menor dataset que ainda falha. Se só acontece com “clientes com muitos registros”, tente criar um caso mínimo que ainda dispare. Se não conseguir, isso indica que o bug pode ser relacionado a volume de dados.
Separe “estado ruim” de “código ruim” resetando o estado de propósito: conta limpa, tenant/dataset novo, build conhecido.
Uma forma prática de manter o repro claro é uma tabela compacta de entradas:
| Given (setup) | When (action) | Expect | Got |
|---|---|---|---|
| User role: Editor; one record with Status=Draft | Click Save | Toast "Saved" + updated timestamp | Button shows spinner then stops; no change |
Faça o repro portátil para que outra pessoa possa rodar rápido:
O caminho mais rápido costuma ser entediante: mude uma coisa, observe, mantenha notas.
Erros comuns:
Um exemplo realista: um ticket diz “Export CSV vem em branco.” Você testa com uma conta admin e vê dados. O usuário tem um papel restrito, e a API retorna uma lista vazia por um filtro de permissão. Se você só consertar a UI para dizer “Sem linhas”, perde a questão real: esse papel deve ter permissão para exportar, ou o produto deveria explicar por que está filtrado?
Após qualquer correção, reroda os passos exatos do repro e então teste um cenário próximo que deveria continuar funcionando.
Você terá respostas melhores de um colega (ou de uma ferramenta) se trouxer um pacote enxuto: passos reproduzíveis, uma camada provável que falha e prova.
Antes de qualquer um mudar código, confirme:
Então faça uma rápida verificação de regressão: tente um papel diferente, uma segunda janela/navegador privado, uma funcionalidade próxima que usa o mesmo endpoint/tabela e um input de borda (vazio, texto longo, caracteres especiais).
Uma mensagem de suporte diz: "O botão Salvar não faz nada no formulário Edit Customer." Um follow-up revela que só acontece para clientes criados antes do mês passado, e apenas quando você muda o e-mail de cobrança.
Comece pela UI e assuma a falha mais simples primeiro. Abra o registro, faça a alteração e procure sinais de que “nada” é na verdade algo: botão desabilitado, toast escondido, mensagem de validação que não renderiza. Depois abra o console do navegador e a aba Network.
Aqui, clicar em Salvar dispara uma requisição, mas a UI nunca mostra o resultado porque o frontend só trata 200 como sucesso e ignora erros 400. A aba Network mostra uma resposta 400 com um corpo JSON como: {\\\"error\\\":\\\"billingEmail must be unique\\\"}.
Agora verifique se a API realmente está falhando: pegue o payload exato da requisição e repita fora da UI. Se falhar também fora da UI, pare de perseguir bugs de estado do frontend.
Depois verifique o banco de dados: por que a unicidade falha apenas em registros antigos? Você descobre que clientes legados compartilham um billing_email placeholder de anos atrás. Uma checagem de unicidade mais nova agora bloqueia salvar qualquer cliente que ainda tenha esse placeholder.
Repro mínimo que você pode passar adiante:
billing_email = [email protected].400 com billingEmail must be unique.Teste de aceitação: quando a API retornar um erro de validação, a UI exibe a mensagem, preserva as alterações do usuário e o erro aponta o campo exato que falhou.
Quando o bug estiver reproduzível e você identificou a camada provável, peça ajuda de forma a obter um patch pequeno e seguro.
Empacote um simples “arquivo de caso”: passos mínimos de repro (com inputs, ambiente, role), esperado vs real, por que você acha que é UI/API/BD, e o menor trecho de log que mostra a falha.
Então faça o pedido estreito:
Se usar uma plataforma de vibe-coding como Koder.ai (koder.ai), essa abordagem de arquivo de caso mantém a sugestão focada. Os snapshots e rollback também ajudam a testar pequenas mudanças com segurança e voltar a uma baseline conhecida.
Passe para um desenvolvedor experiente quando a correção tocar em segurança, pagamentos, migrações de dados ou algo que possa corromper dados em produção. Também passe adiante se a mudança crescer além de um patch pequeno ou se você não conseguir explicar o risco em palavras simples.
Comece reescrevendo em um script reproduzível: quem (papel), onde (página/fluxo), quais entradas exatas (IDs, filtros, payload), o que você esperava e o que viu. Se faltar alguma dessas peças, peça uma conta de exemplo e um ID de registro para poder rodar o mesmo cenário de ponta a ponta.
Escolha um único ambiente e permaneça nele até reproduzir. Registre a versão/build, feature flags, configuração, conta/role de teste e os dados exatos usados. Isso evita “corrigir” um bug que só existe porque sua configuração difere da do repórter.
Faça acontecer duas vezes com os mesmos passos e entradas, então remova tudo que não é necessário. Mire em 3–6 passos a partir de um estado limpo, com um registro reutilizável ou um corpo de requisição. Se não conseguir reduzir, isso costuma indicar dependência de volume de dados, timing ou jobs em background.
Não mude nada ainda. Primeiro execute os passos do repórter exatamente e note o primeiro ponto onde sua experiência diverge (label de botão diferente, campo ausente, texto de erro diferente). Essa primeira discrepância é frequentemente a pista da condição real que dispara o bug.
Verifique se os dados realmente mudaram. Se a API retorna o valor novo, mas a UI mostra o antigo, é provavelmente estado da UI, cache ou re-fetch. Se a resposta da API está errada ou o save não ocorre, foque em API ou BD. Se a linha do BD não atualiza (ou atualiza zero linhas), o problema está na persistência ou nas condições da query.
Confirme que uma requisição de rede é feita ao clicar e inspecione o payload da requisição e o corpo da resposta, não apenas o código de status. Capture um timestamp (com fuso horário) e um identificador de usuário para cruzar com os logs. Um 200 “sucesso” com um corpo inesperado pode ser tão importante quanto um 400/500.
Altere apenas uma coisa por vez: papel do usuário, registro (novo vs legado), navegador/dispositivo, sessão limpa (janela anônima/limpeza de cache) e rede. Testes de variável única mostram qual condição importa e evitam que você persiga coincidências causadas por múltiplas mudanças simultâneas.
Mudar várias variáveis ao mesmo tempo, testar em outro ambiente que não o do repórter e ignorar permissões/roles são os maiores desperdiçadores de tempo. Outro erro comum é consertar o sintoma na UI enquanto um erro de validação na API/BD continua ocorrendo por baixo. Sempre rode o repro exato depois da sua mudança e então teste um cenário próximo.
“Done” significa: o repro mínimo original agora passa, e você re-testou um fluxo próximo que poderia ser impactado. Mantenha a checagem concreta, como um sinal visível de sucesso, resposta HTTP correta ou mudança esperada na linha do BD. Evite “acho que consertei” sem rodar os mesmos inputs na mesma baseline.
Forneça um arquivo de caso enxuto: passos mínimos com inputs exatos, ambiente/build/flags, conta e role de teste, esperado vs real e um trecho de prova (requisição/resposta, texto de erro ou trecho de log com timestamp). Peça o menor patch que faça o repro passar e inclua um mini plano de testes. Se usar Koder.ai, combinar esse arquivo com snapshots/rollback ajuda a testar pequenas mudanças com segurança e reverter se necessário.