No trabalho, nenhum código mudou. O que mudou foi a forma como os clientes inserem os dados. E isso quebrou coisas que nenhum teste existente pegou.
O bug que só aparece quando alguém usa
A motivação pra montar E2E do zero veio de um problema específico.
Você precisava acessar a aplicação pra quebrar. Não era um erro de lógica isolado que um teste unitário pegaria. Era uma combinação de dados reais num fluxo real produzindo um resultado errado que só aparecia na tela. Os clientes chegavam lá antes da gente.
É uma categoria de problema que teste de código não resolve, porque o problema não está no código. Está na interação entre o código, os dados e o ambiente. A forma mais rápida de pegar antes é rodar o fluxo completo do jeito que o usuário roda.
Ficou com smoke tests cobrindo os principais fluxos do produto, configuração pra rodar contra múltiplos ambientes, e notificação no Slack quando o nightly quebra.
A parte mais útil não são os testes em si. É saber antes do cliente reportar.
Autocrop: quando nenhuma ferramenta resolve tudo
Num projeto paralelo que mantenho, passei o fim de semana montando autocrop automático pra imagens.
A ideia inicial era usar o imgproxy Pro, que tem detecção de objeto embutida. Não ficou preciso o suficiente pra variedade de imagens que eu tinha. Fui pro Rekognition, que retorna bounding boxes. Mais controle, mas bounding box tem um limite: é um retângulo. Objetos não são retângulos.
Aí descobri o rembg, que faz algo diferente. Em vez de delimitar uma área, ele cria uma máscara pixel por pixel usando uma rede chamada U2Net, treinada pra segmentação de primeiro plano. O resultado foi bem superior — ele recorta o objeto, não uma caixa em torno dele.
Colocar isso em Lambda foi onde a semana ficou mais lenta. O modelo precisava estar acessível pro processo do Lambda, coloquei em /root, Lambda não lê de lá. Movi pro /opt, chmod 755. O NUMBA tentou escrever cache em diretório read-only, defini NUMBA_CACHE_DIR=/tmp. Depois OOM em imagens maiores, aumentei pra 2048 MB. Cada um levou um ciclo de deploy pra aparecer.
A pipeline final ficou com critérios de aceite diferentes por camada: rembg com padrão rigoroso primeiro. Se não atingir, Rekognition em paralelo com rembg em critérios mais flexíveis. Se nenhum passar, review manual. Nenhuma abordagem de ML funciona pra 100% dos casos — a arquitetura respeita isso.
A review UI que construí em cima foi consequência: se o fallback é humano, precisa de interface decente. O fallback virou feature.
Se quiser o contexto dos anteriores, o #0 e o #1 estão no dev.to. O #2 foi uma semana mais calma e ficou só no LinkedIn.
Top comments (0)