Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -12,3 +12,8 @@ wheels/
# Mypy reports
mypy-reports/
mypy-html-report/

# Coverage artifacts
.coverage
.coverage.*
htmlcov/
6 changes: 6 additions & 0 deletions CLAUDE.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,12 @@ uv run pytest # Run tests
uv run ruff check . # Lint
uv run ruff format . # Format
uv run mypy vgi/ # Type check

# Run tests with coverage (includes subprocess/worker coverage)
uv run coverage run -m pytest --no-cov
uv run coverage combine # Merge subprocess coverage data
uv run coverage report # Show coverage report
uv run coverage html # Generate HTML report in htmlcov/
```

**Before committing**, always run lint and format checks:
Expand Down
36 changes: 36 additions & 0 deletions pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,42 @@ ignore_missing_imports = true
addopts = "--mypy --ruff"
testpaths = ["tests"]

[tool.coverage.run]
# Enable subprocess coverage - automatically patches subprocess.Popen
# to inject coverage measurement into spawned worker processes
patch = ["subprocess"]
# Each subprocess writes to its own data file (.coverage.<hostname>.<pid>)
parallel = true
# Handle SIGTERM gracefully (writes coverage data before exit)
sigterm = true
# Measure branch coverage
branch = true
# What to measure
source = ["vgi"]
# Omit test files and examples from coverage
omit = [
"vgi/examples/*",
"tests/*",
]

[tool.coverage.report]
# Fail if coverage drops below this threshold
fail_under = 80
# Show missing lines in the report
show_missing = true
# Exclude common patterns from coverage
exclude_lines = [
"pragma: no cover",
"if TYPE_CHECKING:",
"if __name__ == .__main__.:",
"@overload",
"raise NotImplementedError",
"\\.\\.\\.", # Ellipsis in stub files
]

[tool.coverage.html]
directory = "htmlcov"

[dependency-groups]
dev = [
"lxml>=6.0.2",
Expand Down
1 change: 1 addition & 0 deletions tests/client/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
"""Client tests package."""
Loading