dennisdoomen / dennisdoomen/packageguard

[Feature]: Add support for Python dependencies (requirements.txt, poetry.lock, uv.lock)

Open
#219 0 comments 0 reactions 0 assignees View on GitHub
enhancement
Dominant language
C#
Stars
74
Forks
4
Avg merge
3h
Merged PRs (30d)
20

Description

### Background and motivation

`IProjectAnalysisStrategy` was clearly designed to make new ecosystems possible, and NuGet plus the npm family are already covered. Python is the natural next step: most .NET organisations have Python somewhere (data work, tooling, ML, scripts), and it is currently unscanned. Being able to point one tool at a polyglot repository and get one policy applied across all of it is a meaningful advantage over per-ecosystem tooling.

**Proposal**

Add a Python analysis strategy covering the common dependency declarations:

- `requirements.txt` — ubiquitous, but frequently unpinned, so the resolved versions may need `pip` involvement
- `poetry.lock` and `pyproject.toml` — fully pinned with hashes, the easiest case to handle correctly
- `uv.lock` — increasingly common and well structured
- `Pipfile.lock` — older but still in use

Design points:

- **Metadata source.** PyPI's JSON API (`https://pypi.org/pypi/{name}/{version}/json`) provides license, homepage and project URLs, mirroring what `NpmRegistryMetadataFetcher` does today.
- **License quality is poor.** Python packages often express licenses through Trove classifiers (`License :: OSI Approved :: MIT License`) rather than SPDX identifiers, and the free-text `license` field is inconsistent. A classifier-to-SPDX mapping is needed, and the existing GitHub fallback fetcher will earn its keep here.
- **Transitive resolution.** `requirements.txt` without a lock file does not describe the full graph. Either resolve via a tool such as `uv pip compile`, or be explicit that unlocked requirements are analysed for direct dependencies only. Silently under-reporting would be worse than saying so.
- **Vulnerability data.** OSV covers PyPI well, so `OsvRiskEnricher` should extend with little change.
- **Environment markers and extras.** `package[extra]` and `; python_version < "3.11"` markers affect what is actually installed and need at least basic handling.
- **Virtual environments.** Unlike `dotnet restore`, running `pip install` to resolve is invasive. Reading lock files without touching the environment should be the default.

Go modules (`go.sum` is fully pinned, and `pkg.go.dev` exposes license data) and Cargo (`Cargo.lock` plus crates.io, where SPDX expressions are the norm) are both plausible follow-ups; both are cleaner data sources than Python, but Python is the more common companion to .NET.

### Alternative Concerns

- Teams can run `pip-licenses` or `pip-audit` separately, but then licence policy lives in two places and drifts.
- Restricting scope to lock files only would be a smaller, more reliable first version, and may be the right way to start.

### Are you willing help with a pull-request?

No

Contributor guide

Open the contributing guide

Research direction

Start by reading IProjectAnalysisStrategy, NpmRegistryMetadataFetcher, and OsvRiskEnricher to understand the existing strategy, metadata, and vulnerability entry points. Compare the current NuGet and npm coverage, then narrow the first implementation scope and define tests for parsing Python dependency declarations, reporting metadata and licenses, and OSV enrichment.

Written by the indexing model from the issue text.

Assessment

Tech stack
csharp, python
Domain
security, tooling
Issue type
Feature
Difficulty
5/5
Estimated time
Over a week
Activity status
Quiet
Clarity
Needs clarification
Newbie friendliness
35/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.