113 lines
3.5 KiB
Markdown
113 lines
3.5 KiB
Markdown
# Discover Project Test Patterns
|
||
|
||
Run this discovery process once at the start of every autotest-writer session.
|
||
Cache results — do not repeat searches for the same project.
|
||
|
||
## 1. Framework Detection
|
||
|
||
Search for test dependencies in `pyproject.toml` or `requirements*.txt`:
|
||
|
||
| Found | Framework |
|
||
|-------|-----------|
|
||
| `pytest` | pytest (default assumption) |
|
||
| `unittest` only | stdlib unittest |
|
||
| `anyio`, `pytest-asyncio` | async pytest |
|
||
| `hypothesis` | property-based testing present |
|
||
|
||
If none found — default to **pytest**.
|
||
|
||
## 2. Test File Layout
|
||
|
||
Run a glob search for `test_*.py` and `*_test.py` files.
|
||
Determine:
|
||
- **Root test folder**: `tests/`, `test/`, inline next to source, or mixed
|
||
- **Naming convention**: `test_{module}.py` or `{module}_test.py`
|
||
- **Mirrors source tree?** e.g. `src/auth/login.py` → `tests/auth/test_login.py`
|
||
|
||
## 3. conftest.py Analysis
|
||
|
||
Read all `conftest.py` files found (root + subdirectories).
|
||
Extract:
|
||
- All fixture names and their scopes (`function`, `session`, `module`)
|
||
- Factory fixtures (return a callable/class)
|
||
- Common parametrize patterns
|
||
- Any custom pytest plugins or hooks registered
|
||
|
||
## 4. Read Sample Tests
|
||
|
||
Read **2–3 representative test files** (pick files that seem most complete, not trivial ones).
|
||
Extract the following patterns:
|
||
|
||
### Import style
|
||
```python
|
||
# Note: stdlib first? third-party second? local last?
|
||
# Note: are there "from __future__ import annotations"?
|
||
```
|
||
|
||
### Class vs function tests
|
||
- Are tests in classes (`class TestLogin:`) or bare functions?
|
||
- If classes — do they inherit from anything?
|
||
|
||
### Assertion style
|
||
- Plain `assert a == b`
|
||
- `assert a == b, "message"`
|
||
- Custom matchers: `assert_that(a).equals(b)`, `expect(a).to.equal(b)`
|
||
|
||
### Mock / patch style
|
||
- `unittest.mock.patch` as decorator
|
||
- `unittest.mock.patch` as context manager
|
||
- `pytest-mock` via `mocker` fixture
|
||
- `MagicMock` / `AsyncMock` / `create_autospec`
|
||
|
||
### Async style
|
||
- `@pytest.mark.asyncio` + `async def test_`
|
||
- `anyio` backend marker
|
||
- Synchronous wrappers around async code
|
||
|
||
### Parametrize style
|
||
```python
|
||
@pytest.mark.parametrize("input,expected", [...])
|
||
```
|
||
or inline in class docstring (hypothesis)?
|
||
|
||
## 5. Factory / Builder Patterns
|
||
|
||
Search for:
|
||
- `factory_boy` — `UserFactory`, `PostFactory` classes
|
||
- `pytest-factoryboy` — `register()` usage
|
||
- Custom builder fixtures that return objects
|
||
- `faker` usage for test data generation
|
||
|
||
## 6. Database / External Service Patterns
|
||
|
||
- Does the project use `pytest-django`, `pytest-sqlalchemy`, or custom DB fixtures?
|
||
- Are there transaction rollback fixtures (`db`, `transactional_db`)?
|
||
- Are HTTP calls mocked via `responses`, `httpretty`, `respx`, or `pytest-httpx`?
|
||
- Is there a test database URL in `.env.test` or `pytest.ini`?
|
||
|
||
## 7. Markers and Config
|
||
|
||
Read `pytest.ini`, `setup.cfg`, or `[tool.pytest.ini_options]` in `pyproject.toml`.
|
||
Note:
|
||
- Custom markers (`@pytest.mark.integration`, `@pytest.mark.slow`)
|
||
- `asyncio_mode` setting (`auto` or `strict`)
|
||
- `testpaths` — where pytest looks for tests
|
||
- Any `filterwarnings` that should be preserved
|
||
|
||
## Output Format
|
||
|
||
Summarize findings as:
|
||
```
|
||
Framework: pytest 8.x
|
||
Async: pytest-asyncio, asyncio_mode=auto
|
||
Test root: tests/
|
||
Naming: test_{module}.py mirroring src/
|
||
Classes: no (bare functions)
|
||
Fixtures: conftest.py at root; session-scoped db_engine, function-scoped db_session
|
||
Factories: factory_boy (UserFactory, ProjectFactory)
|
||
Mocks: pytest-mock (mocker fixture)
|
||
HTTP mocks: respx
|
||
Markers: integration, slow, unit
|
||
Assertions: plain assert
|
||
```
|