utils/dep_freshness/parsers/rust.py
Krzysztof kuhy Rudnicki 92d7151bdf
Some checks are pending
dependency freshness / dependencies on newest stable (push) Waiting to run
file length / file-length (push) Waiting to run
md-naming / markdown naming convention (push) Waiting to run
palette drift / palette (push) Waiting to run
shared gate tests / gate unit tests (push) Waiting to run
dep_freshness: accept Cargo's =x.y.z as the exact pin it is
Cargo's bare `"0.19.1"` is a caret range; its exact operator is a single
`=`. The shared EXACT regex only knew pip's `==`, so the one form that is
actually an exact pin in Cargo was reported as "not exact-pinned" against
itself (platformer/proto-bevy, 2026-09-06). Strip the operator in the Rust
parser; the constraint string keeps it so the report shows what is written.

Co-Authored-By: Claude Code <noreply@anthropic.com>
2026-09-06 18:07:10 +02:00

61 lines
2.0 KiB
Python

"""`Cargo.toml` -> crates.io dependencies.
A dependency is either a bare string (`serde = "1.0.229"`) or a table with a
`version` key; path and git dependencies have no registry version and are
skipped. Cargo's bare `"1.0"` is a caret range, so only a full three-part
version counts as pinned — `"1.0"` is reported unpinned, which is correct.
Cargo's own exact operator is a single `=` (`"=1.0.229"`), which the shared
EXACT regex does not know (it spells pip's `==`), so it is stripped here.
"""
from __future__ import annotations
from pathlib import Path
import tomllib
from dep_freshness._tables import CARGO
from dep_freshness.models import Dep
from dep_freshness.parsers._lines import index
from dep_freshness.versions import exact_pin
_SECTIONS = (
("dependencies", False),
("dev-dependencies", True),
("build-dependencies", True),
)
def parse(path: Path) -> list[Dep]:
try:
data = tomllib.loads(path.read_text(encoding="utf-8"))
except (OSError, tomllib.TOMLDecodeError):
return []
lines = index(path)
deps: list[Dep] = []
for section, is_dev in _SECTIONS:
for name, spec in (data.get(section) or {}).items():
if isinstance(spec, dict):
if "path" in spec or "git" in spec:
continue
constraint = str(spec.get("version") or "")
else:
constraint = str(spec)
if not constraint:
continue
pinned = exact_pin(constraint.strip().removeprefix("="))
if pinned and pinned.count(".") < 2:
pinned = None # "1.0" is a caret range in Cargo, not a pin
deps.append(
Dep(
ecosystem=CARGO,
name=str(name),
constraint=constraint,
path=path,
line=lines.get(str(name), 0),
pinned=pinned,
dev=is_dev,
)
)
return deps