Skip to content

Commit 8870937

Browse files
committed
docs: add uv package management documentation
- Add "Package management (uv)" section to root AGENTS.md - Update all test commands in tests/AGENTS.md to use uv run - Update .envrc to unset VIRTUAL_ENV and show uv commands - Add auto-sync for uv dependencies when .venv is stale
1 parent 43d6223 commit 8870937

3 files changed

Lines changed: 77 additions & 40 deletions

File tree

.envrc

Lines changed: 18 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,17 +2,31 @@
22

33
export PROJECT_NAME="${PROJECT_NAME:-$(basename "$PWD")}"
44

5+
# Clear any conflicting VIRTUAL_ENV from other projects
6+
# This project uses uv with its own .venv/
7+
unset VIRTUAL_ENV
8+
59
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
610
echo "direnv: Loaded $PROJECT_NAME"
711
echo ""
12+
echo "Package management: uv (always use 'uv run' for Python commands)"
13+
echo ""
814
echo "Quick start:"
9-
echo " make help - Show available targets"
10-
echo " make update - Collect tool versions (requires network)"
11-
echo " make audit - Run audit from snapshot (fast, offline)"
15+
echo " uv sync --extra dev - Install/sync dependencies"
16+
echo " uv run python -m pytest - Run all tests"
17+
echo " uv run python audit.py --help - Show CLI options"
1218
echo ""
13-
echo "First time? Run: make update && make audit"
19+
echo "First time? Run: uv sync --extra dev"
1420
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
1521

22+
# Auto-sync uv dependencies if .venv is missing or stale
23+
if command -v uv &> /dev/null; then
24+
if [ ! -d ".venv" ] || [ "pyproject.toml" -nt ".venv" ]; then
25+
echo "→ Running uv sync --extra dev..."
26+
uv sync --extra dev --quiet
27+
fi
28+
fi
29+
1630
# Load environment files if they exist (Makefile handles this too)
1731
# Uncomment if you want direnv to export these variables
1832
# use dotenv .env.default

AGENTS.md

Lines changed: 25 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -13,13 +13,30 @@
1313
- Ask before: heavy deps, full rewrites, breaking changes
1414
- Never commit secrets, PII, or credentials
1515

16+
## Package management (uv)
17+
18+
**This project uses [uv](https://docs.astral.sh/uv/) for package management.** Always use `uv run` to execute Python commands.
19+
20+
```bash
21+
# Sync dependencies (run after clone or when pyproject.toml changes)
22+
uv sync --extra dev
23+
24+
# Run any Python command
25+
uv run python -m pytest # Run tests
26+
uv run python audit.py ripgrep # Run audit script
27+
uv run python -m flake8 # Run linter
28+
```
29+
30+
**Why uv?** Fast dependency resolution, proper lockfile support, and isolated environments without manual venv activation.
31+
1632
## Minimal pre-commit checks
1733

1834
```bash
19-
make lint # flake8 (required)
20-
make lint-types # mypy (optional)
21-
./scripts/test_smoke.sh # Smoke tests (required)
22-
make audit # Verify core workflows
35+
uv run python -m pytest # All tests (required)
36+
uv run python -m flake8 cli_audit tests # flake8 (required)
37+
uv run python -m mypy cli_audit # mypy (optional)
38+
./scripts/test_smoke.sh # Smoke tests (required)
39+
uv run python audit.py --help # Verify CLI works
2340
```
2441

2542
## Index of scoped AGENTS.md
@@ -32,11 +49,13 @@ make audit # Verify core workflows
3249

3350
| Command | Purpose |
3451
|---------|---------|
52+
| `uv run python -m pytest` | Run all tests |
53+
| `uv run python -m pytest -x` | Run tests, stop on first failure |
54+
| `uv run python audit.py ripgrep` | Single tool audit |
55+
| `uv run python audit.py --help` | Show CLI options |
3556
| `make audit` | Render from snapshot (<100ms) |
3657
| `make update` | Collect fresh versions (~7s) |
3758
| `make upgrade` | Interactive upgrade guide |
38-
| `make upgrade-all` | Complete 5-stage system upgrade |
39-
| `python3 audit.py ripgrep` | Single tool audit |
4059

4160
## Project overview
4261

tests/AGENTS.md

Lines changed: 34 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -35,19 +35,19 @@ tests/
3535

3636
**Requirements:**
3737
```bash
38-
# Python 3.10+ with pytest
39-
python3 --version # 3.10, 3.11, 3.12, 3.14 tested
38+
# Python 3.14+ with uv package manager
39+
python3 --version # 3.14 required
40+
uv --version # uv required
4041

41-
# Install test dependencies
42-
pip install -e ".[dev]"
43-
# OR
44-
uv pip install -e ".[dev]"
42+
# Sync all dependencies (including dev)
43+
uv sync --extra dev
4544
```
4645

4746
**Test dependencies (from pyproject.toml):**
4847
- pytest — Test framework
4948
- pytest-cov — Coverage reporting
50-
- pytest-mock — Mocking utilities (if used)
49+
- pytest-mock — Mocking utilities
50+
- pytest-xdist — Parallel test execution
5151

5252
**Test environment variables:**
5353
```bash
@@ -58,33 +58,36 @@ CLI_AUDIT_TIMEOUT_SECONDS=1 # Fast timeout for tests
5858

5959
## Build & tests
6060

61-
**Run all tests:**
61+
**Run all tests (use uv run):**
6262
```bash
63-
# From project root
64-
python3 -m pytest tests/ -v
63+
# From project root - ALWAYS use uv run
64+
uv run python -m pytest
65+
66+
# Verbose output
67+
uv run python -m pytest -v
6568

6669
# With coverage
67-
python3 -m pytest tests/ -v --cov=cli_audit --cov-report=html
70+
uv run python -m pytest --cov=cli_audit --cov-report=html
6871

69-
# Parallel execution
70-
python3 -m pytest tests/ -v -n auto
72+
# Parallel execution (fast)
73+
uv run python -m pytest -n auto
7174
```
7275

7376
**Run specific test files:**
7477
```bash
7578
# Single test file
76-
python3 -m pytest tests/test_config.py -v
79+
uv run python -m pytest tests/test_config.py -v
7780

7881
# Single test class
79-
python3 -m pytest tests/test_config.py::TestToolConfig -v
82+
uv run python -m pytest tests/test_config.py::TestToolConfig -v
8083

8184
# Single test function
82-
python3 -m pytest tests/test_config.py::TestToolConfig::test_tool_config_defaults -v
85+
uv run python -m pytest tests/test_config.py::TestToolConfig::test_tool_config_defaults -v
8386
```
8487

8588
**Run integration tests:**
8689
```bash
87-
python3 -m pytest tests/integration/ -v
90+
uv run python -m pytest tests/integration/ -v
8891
```
8992

9093
**Smoke test (quick validation):**
@@ -95,13 +98,13 @@ python3 -m pytest tests/integration/ -v
9598
**Filter tests by marker:**
9699
```bash
97100
# Run only slow tests
98-
python3 -m pytest -m slow
101+
uv run python -m pytest -m slow
99102

100103
# Skip slow tests
101-
python3 -m pytest -m "not slow"
104+
uv run python -m pytest -m "not slow"
102105

103106
# Run only unit tests
104-
python3 -m pytest -m unit
107+
uv run python -m pytest -m unit
105108
```
106109

107110
## Code style & conventions
@@ -206,7 +209,7 @@ def test_tool_execution(mock_run):
206209

207210
Before committing test changes:
208211

209-
- [ ] **All tests pass:** `pytest tests/ -v` succeeds
212+
- [ ] **All tests pass:** `uv run python -m pytest` succeeds
210213
- [ ] **No skipped tests:** Fix or document skipped tests
211214
- [ ] **Coverage maintained:** New code has corresponding tests
212215
- [ ] **Isolation:** Tests don't depend on execution order
@@ -217,7 +220,7 @@ Before committing test changes:
217220
- [ ] **Documentation:** Complex test logic has comments
218221

219222
**Integration test checklist:**
220-
- [ ] E2E tests pass: `pytest tests/integration/ -v`
223+
- [ ] E2E tests pass: `uv run python -m pytest tests/integration/ -v`
221224
- [ ] Real environment tested: Not just mocks
222225
- [ ] Idempotent: Can run multiple times safely
223226
- [ ] Reasonable timeout: Integration tests <30s each
@@ -330,38 +333,39 @@ def test_snapshot_write(tmp_path):
330333
**Debugging failing tests:**
331334
```bash
332335
# Run with verbose output
333-
python3 -m pytest tests/test_config.py -vv
336+
uv run python -m pytest tests/test_config.py -vv
334337

335338
# Show print statements
336-
python3 -m pytest tests/test_config.py -s
339+
uv run python -m pytest tests/test_config.py -s
337340

338341
# Stop on first failure
339-
python3 -m pytest tests/ -x
342+
uv run python -m pytest -x
340343

341344
# Enter debugger on failure
342-
python3 -m pytest tests/ --pdb
345+
uv run python -m pytest --pdb
343346

344347
# Show last failed tests
345-
python3 -m pytest --lf
348+
uv run python -m pytest --lf
346349
```
347350

348351
**Common issues:**
349-
- **Import errors:** Run from project root, check PYTHONPATH
352+
- **Import errors:** Run `uv sync --extra dev` first, ensure uv run is used
350353
- **Fixture not found:** Check fixture scope and location
351354
- **Test order dependency:** Tests should be independent, fix test isolation
352355
- **Slow tests:** Mock external calls, use tmp_path, check for real network/subprocess
353356
- **Flaky tests:** Usually timing issues, mock time-dependent operations
357+
- **VIRTUAL_ENV warning:** Run `deactivate` first if another venv is active
354358

355359
**Test coverage:**
356360
```bash
357361
# Generate coverage report
358-
python3 -m pytest tests/ --cov=cli_audit --cov-report=html
362+
uv run python -m pytest --cov=cli_audit --cov-report=html
359363

360364
# View report
361365
open htmlcov/index.html
362366

363367
# Show missing lines
364-
python3 -m pytest tests/ --cov=cli_audit --cov-report=term-missing
368+
uv run python -m pytest --cov=cli_audit --cov-report=term-missing
365369
```
366370

367371
## House rules

0 commit comments

Comments
 (0)