Skip to main content

CHAIN003 — git-dependency-without-rev

PropertyValue
Rule IDCHAIN003-git-dependency-without-rev
Dimensionsupply_chain
SeverityMedium
Analyzer kindProjectLevel
LanguagesRust (all projects)

What it detects​

CHAIN003 fires for each entry in [dependencies] or [dev-dependencies] that has a git = "..." key without a rev = "..." or tag = "..." sibling key.

A branch-only git dependency is considered unpinned:

# Flagged — branch tip moves between builds
mycrate = { git = "https://github.com/example/mycrate", branch = "main" }

# Flagged — no pin at all
mycrate = { git = "https://github.com/example/mycrate" }

Why it matters​

A git dependency without a stable pin (rev or tag) resolves to whatever commit the branch points at at build time. Two builds on different days may resolve to different commits, making the build non-reproducible.

More critically, if the upstream repository is compromised or the branch is force-pushed, a dependency that was previously benign could introduce malicious code into your build without any change to Cargo.toml.

Examples — flagged​

[dependencies]
my-lib = { git = "https://github.com/example/my-lib" }
other-lib = { git = "https://github.com/example/other", branch = "dev" }

Examples — not flagged​

[dependencies]
# Pinned by commit hash (preferred)
my-lib = { git = "https://github.com/example/my-lib", rev = "a1b2c3d4" }

# Pinned by tag (acceptable)
other-lib = { git = "https://github.com/example/other", tag = "v1.2.3" }

How to fix​

Identify the exact commit you want to use and pin it with rev:

git ls-remote https://github.com/example/my-lib HEAD
# Copy the SHA and add: rev = "<sha>"

Or use a specific tagged release:

my-lib = { git = "https://github.com/example/my-lib", tag = "v1.2.3" }

When the upstream crate is published on crates.io, prefer using the registry version instead of a git dependency — this gives you reproducible resolution with Cargo.lock and access to cargo audit advisories.

Suppression​

To suppress globally for a project, add the rule to the engine's ignore list:

[ignore]
rules = ["CHAIN003-git-dependency-without-rev"]

References​