Roadmap — Testes (galho 12)
Roadmap-folha do galho Python/Testes. Fase Adepto — pytest, fixtures, mocking, coverage, TDD (Percival & Gregory como fonte). Spec: 2026-07-09-python-trilha-design. EXEMPLAR de estrutura: Python/Segurança/index.md e Python/Segurança/roadmap.md (galho anterior, mesmo padrão).
Roster não pré-cravado no spec (só a descrição de alto nível “pytest, fixtures, mocking, coverage, TDD”) — desenhado nesta sessão seguindo o mesmo playbook dos Galhos 5, 7, 8, 9, 10 e 11. Quarto galho do bloco “Backend e arquitetura” (9-13) — testa o que os Galhos 9-11 construíram.
Fronteira cravada: a teoria e estratégia de testes (pirâmide, tipos de teste, test doubles como conceito, flaky tests, mutation testing) já está coberta de forma stack-agnóstica em Testes (21 notas conceituais + ferramental Java/JS). Este galho é só o ferramental pytest aplicado ao código Python já construído na trilha — nenhuma nota deste galho reexplica pirâmide de testes ou taxonomia de test doubles, só referencia.
Tabela-resumo
| Métrica | Valor |
|---|---|
| Total de notas | 9 |
| ⬜ pendente | 0 |
| ✅ feita | 9 |
| 🔄 em andamento | 0 |
| % concluído | 100% |
Notas
01 - pytest fundamentos — anatomia, discovery e assert introspection
- Estado: ✅ feita (2026-07-11) · fase: Adepto
- Escopo: por que
pytestdominou sobreunittest(assert nativo do Python com introspecção automática via rewrite de bytecode, vs.self.assertEqualverboso), anatomia de um teste (test_*.py, funçãotest_*, sem herança de classe obrigatória), discovery automático, markers básicos (@pytest.mark.skip/xfail), rodando compytest -v/-k/-x. Referencia a pirâmide de testes de Engenharia/Testes sem repetir. - Resultado: 483 linhas / 4567 palavras. Abre com dev vindo de Java/JUnit surpreso com assert rewriting; cobre anatomia mínima, discovery por convenção (diagrama Mermaid), markers, flags de execução, contraste tabelado com
unittest, exemplo de negócio (desconto progressivo) fechando compytest.approx.
02 - Fixtures — escopos, yield e conftest.py
- Estado: ✅ feita (2026-07-11) · fase: Adepto
- Escopo:
@pytest.fixture, injeção por nome de parâmetro (mecanismo de DI do próprio pytest), escopos (function/class/module/session) e quando usar cada um, fixtures comyieldpra setup/teardown (paralelo aoDependscomyielddo Galho 10 nota 04 — mesma ideia, contextos diferentes),conftest.pycomo compartilhamento entre arquivos de teste sem import explícito. - Resultado: 482 linhas / 5949 palavras. Abre com fixture
sessionguardando lista mutável causando falha dependente de ordem entre testes; desenvolve mecanismo de injeção por nome, os 4 escopos com regra prática, paraleloyieldcomDepends()do Galho 10 (sequenceDiagram),conftest.pycom herança por diretório.
03 - Parametrização e organização de suíte
- Estado: ✅ feita (2026-07-11) · fase: Adepto
- Escopo:
@pytest.mark.parametrize(evita duplicação de teste quase-idêntico variando só o dado de entrada),idscustomizados pra legibilidade do output, marks customizados registrados empytest.ini/pyproject.toml, organização de diretório (tests/unit/tests/integration, espelhando estrutura do código), fixtures parametrizadas. - Resultado: 465 linhas / 4921 palavras. Abre com 15 testes quase-idênticos de CPF onde um copy-paste deixa um assert invertido passar despercebido; desenvolve
parametrize/ids, marks customizados com-m "not slow"(pre-commit vs CI), organizaçãotests/unit/tests/integration, fixtures parametrizadas.
04 - Mocking com unittest.mock e pytest-mock
- Estado: ✅ feita (2026-07-11) · fase: Adepto
- Escopo:
Mock/MagicMock/patchda biblioteca padrãounittest.mock,pytest-mockcomo wrapper mais ergonômico (fixturemocker),patchcomo context manager vs decorator vs fixture,autospec(por que mock sem spec deixa passar erro de assinatura), quando mockar vs quando NÃO mockar (referencia a filosofia de test doubles de Engenharia/Testes sem repetir a taxonomia completa). - Resultado: 502 linhas / 4377 palavras. Abre com mock sem spec mascarando um refactor que renomeou método, bug só explodindo em produção; desenvolve
Mock/MagicMock, os 3 estilos depatch,spec/autospec=True, regra prática de quando mockar (fronteiras externas) vs não mockar (código interno), exemplo de mock de consulta de CEP externa.
05 - Testando a API REST — TestClient e dependency overrides
- Estado: ✅ feita (2026-07-11) · fase: Adepto
- Escopo:
TestClientdo FastAPI (Starlette por baixo, faz requisição sem subir servidor real),app.dependency_overrides(já mencionado no Galho 10 nota 04 — agora desenvolvido: como trocarget_current_user/get_dbpor versões de teste), Django test client/pytest-djangocomo equivalente. Teste de um endpoint completo da API de Tarefas (Galho 10) validando status code + shape da resposta. - Resultado: 471 linhas / 6188 palavras. Abre com regressão de Broken Access Control não pega por testes só manuais via Swagger; desenvolve
TestClient(transport ASGI em processo),dependency_overridestrocandoget_db/get_current_user, contraste compytest-django. Teste mais rico: criar tarefa como usuário A, trocar override pra usuário B, validar 404 — regressão automatizada do fix de Broken Access Control do Galho 11.
06 - Testando a camada de persistência — banco de teste e rollback
- Estado: ✅ feita (2026-07-11) · fase: Adepto
- Escopo: banco de teste isolado (SQLite in-memory como opção rápida mas com ressalva honesta — não é 100% fiel ao Postgres de produção, referencia a nota 06 do Galho 9 sobre isolation levels), Postgres real via
testcontainers-pythoncomo alternativa mais fiel, fixture de sessão com rollback automático entre testes (transação que nunca commita de verdade), factory de dados de teste (menção afactory_boycomo padrão de mercado). - Resultado: 390 linhas / 5415 palavras. Abre com migração de “recriar schema a cada teste” (lento) pra
scope="session"sem isolamento (dado órfão vazando entre testes); desenvolve trade-off SQLite vs Postgres real via testcontainers, fixture de rollback comconnection.begin()/SAVEPOINT,factory_boybreve.
07 - Coverage — pytest-cov e o que ele não mede
- Estado: ✅ feita (2026-07-11) · fase: Adepto
- Escopo:
pytest-cov,--cov-report, gate de coverage em CI, e a ressalva honesta central da nota — 100% de coverage de LINHA não significa 100% de coverage de CASO (umiftestado só no caminho feliz conta como “coberto” mesmo sem testar oelse) — referencia mutation testing como o próximo degrau (conceito já em Engenharia/Testes, aqui só menção demutmutcomo ferramenta Python equivalente ao PIT do Java). - Resultado: 376 linhas / 5344 palavras. Abre com fintech “98% coverage” tendo bug de inversão de parâmetros não pego porque o teste só fazia
assert resultado is not None; desenvolvepytest-covtécnico, distinção execução vs correção,--cov-branch, 2 diagramas Mermaid (3 degraus de rigor + pipeline). Mutation testing só referenciado (mutmut).
08 - TDD na prática com pytest
- Estado: ✅ feita (2026-07-11) · fase: Adepto
- Escopo: o ciclo red-green-refactor aplicado com
pytestnum caso real pequeno (não reensina a filosofia de TDD, que é conceitual e agnóstica — referencia Engenharia/Testes e cita Percival & Gregory como fonte do rigor “outside-in” usado no livro-fonte da trilha), demonstra o ciclo com um caso de negócio da API de Tarefas (ex: uma regra nova — “não permitir criar tarefa com prazo no passado”). - Resultado: 220 linhas / 3312 palavras (aplicação prática deliberadamente mais curta — filosofia já coberta em Engenharia/Testes). Ciclo RED-GREEN-REFACTOR completo com
data_limiteno passado: RED com TestClient, GREEN comifsolto no handler, REFACTOR movendo pra@field_validatorsem tocar no teste. Outside-in de Percival & Gregory, reflexão honesta sobre quando TDD compensa vs atrapalha.
09 - Capstone — a suíte de testes da API de Tarefas
- Estado: ✅ feita (2026-07-11) · fase: Adepto
- Escopo: recapitula o galho construindo a suíte de testes completa pra API de Tarefas blindada na capstone do Galho 11 — testes unitários (lógica pura), testes de integração (
TestClient+ banco de teste), e testes de SEGURANÇA validando os fixes do Galho 11 (teste que confirma que um usuário não acessa tarefa de outro — regressão de Broken Access Control; teste que confirma que o endpoint de busca não é mais vulnerável a SSTI; teste de rate limiting). Cenário prático integrador. Aponta para o Galho 13 (Arquitetura e Design Patterns) como próximo passo — a suíte de testes revela acoplamentos que motivam Repository/Unit of Work formal. - Resultado: 633 linhas / 7097 palavras. Árvore
tests/{unit,integration,security}/completa amarrando as 8 notas do galho ao código real das capstones dos Galhos 9-11. Núcleo original emtests/security/: regressão de Broken Access Control nos 4 verbos HTTP, SSTI provada por asserção negativa ({{7*7}}nunca vira “49”), rate limiting estourando 429 na 6ª tentativa — tratados como não-opcionais no CI. 4 diagramas Mermaid, coverage sintético com leitura honesta. Fecha apontando pro Galho 13 (padrões Repository/UoW já aparecendo informalmente na suíte).
Galho 12 completo — 9/9 notas (2026-07-11)
pytest fundamentos (01) → fixtures/escopos (02) → parametrização (03) → mocking (04) → testando a API REST (05) → testando persistência (06) → coverage e seus limites (07) → TDD na prática (08) → capstone com suíte completa (unit + integração + segurança) validando o hardening do Galho 11 (09). Todas as notas referenciam a teoria stack-agnóstica de Engenharia/Testes sem repeti-la — o galho é 100% ferramental
pytestaplicado ao código real construído nos Galhos 9-11. Próximo da trilha: Galho 13 — Arquitetura e Design Patterns.
Decisões e fronteiras registradas
- Pirâmide de testes, taxonomia de test doubles, flaky tests, mutation testing como conceito → Testes; aqui é só a aplicação
pytest. - Filosofia de TDD (red-green-refactor como disciplina, outside-in vs inside-out) → também Engenharia/Testes; a nota 08 aqui só aplica o ciclo com ferramental Python.
unittestlegado (classeTestCase,self.assert*) mencionado só como contraste histórico na nota 01, não desenvolvido a fundo — o ferramental moderno épytest.- Testes de carga/performance (
locust) ficam fora do escopo deste galho — são tema de Operação/produção, não de correção funcional.