Files
coding-agent-rules/testing.md
2025-10-04 16:16:05 -04:00

90 lines
4.2 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
---
trigger: always_on
---
## General Principles
- Write unit tests for new features prior to implementing the feature.
- Write unit tests for utilities and components.
- Maintain 100% test coverage (backend). Frontend coverage threshold follows CI config (≥90% or 100% for symmetry).
- Unit tests should never make external calls. Integration tests may call externals.
- Minimize fixtures for generating inputs; prefer explicit inline inputs/expectations.
- Tests should be written as functions (avoid class-based tests).
- Use descriptive, intention-revealing names (e.g., `isCreated`, `hasError`) and prefer iteration/modularization over duplication.
## Test Structure
### Top-level Layout
- `tests/unit/` for pure unit tests (no external I/O).
- `tests/integration/` for tests allowed to hit external services.
### Granular Python Unit Test Organization
1. Use a directory per module under test (e.g., `tests/unit/app/services/estimating/`).
2. Within that directory, use a file per function under test (e.g., `test_calculate_estimate.py`).
3. Keep unit and integration tests in separate trees: `tests/unit/` and `tests/integration/`.
### Naming and Scope
- Only test functionality in the module under test; dont re-test validation or logic implemented elsewhere.
- Do not introduce coverage-only test files (e.g., files named with “additional_coverage”, “remaining_branches”, “misc_coverage”).
- When adding a new test file, name it by feature or unit under test (e.g., `test_service_delete_update.py`).
## Backend (FastAPI) Testing
### Framework
- Pytest
### Coverage and Practices
- Prefer tests over no-cover.
- Avoid `# pragma: no cover` except in strictly justified cases:
- Optional dependency branches or platform guards
- Defensive/unreachable paths in supported environments
- Use `pytest-mock`s `mocker` fixture for mocking.
- Use monkeypatches to control `time.sleep`, `random.random`, etc., to keep tests fast/deterministic.
- For network-like behavior, write light fakes with only the attributes used by the code under test.
- If a safety guard exists (e.g., a best-effort `close()`), add a micro-test to exercise it.
### Commands
- Full suite (CI-like): `bash scripts/ci/backend-test.sh`
- Ad-hoc (from `backend/`):
- All tests (with dev extras): `uv run --with .[dev] -m pytest`
- With coverage: `uv run --with .[dev] -m pytest --cov=app --cov-report=term-missing`
- Single test/file: `uv run --with .[dev] -m pytest app/tests/unit/path/to/test_file.py::test_case`
### Notes
- Dev extras defined under `[project.optional-dependencies].dev` in `backend/pyproject.toml` and include `pytest`, `pytest-cov`.
- Pytest config lives under `[tool.pytest.ini_options]` in `backend/pyproject.toml` (e.g., `testpaths = ["app/tests"]`).
- Quick run without extras (no coverage): `uv run -m pytest` (no `pytest-cov`).
## Frontend (React or React Native) Testing
### Framework
- Jest + Testing Library (React) or Jest + React Native Testing Library (React Native)
### Mocking Guidance
- Avoid mocking React/React Native primitives unless necessary.
- Mock network via MSW.
### Commands
- Full suite (CI-like): `bash scripts/ci/frontend-test.sh`
- Ad-hoc (from `frontend/`):
- npm: `npm run lint` then `npm test -- --coverage`
- pnpm: `pnpm run lint` then `pnpm test -- --coverage`
## End-to-End (E2E) Testing
- Implement E2E tests for critical flows.
- Choose an appropriate framework based on the frontend:
- Web (React): Playwright or Cypress
- React Native: Detox
- Keep E2E focused on user-critical paths; avoid duplicating unit/integration coverage.
## CI Expectations and Consistency
- CI runs from `.gitea/workflows/`.
- Required checks:
- Backend: ruff, mypy, tests with coverage ≥100%.
- Frontend: eslint, jest with coverage thresholds (≥90% or 100% for symmetry).
- No merges to main without green pipelines.
- Use `scripts/ci/*` to mirror CI logic locally.
## Development Phase Testing (Pre-deployment)
- Update tests in the same PR when API contracts change (request/response shapes, validation, or status codes).
- Refresh example payloads in schemas and test fixtures together to prevent drift.
- Prefer targeted API integration tests for critical endpoints to validate schema and docs alignment.