Approve it only with a reason and a pin. A git URL, GitHub shorthand or tarball URL dependency bypasses the version history of a registry, and without a commit hash it can follow a branch that moves. Ask why a published release will not work, and require an exact commit.
What npm allows
The npm package.json documentation lists the forms a dependency version can take: a semver range, a dist-tag such as latest, a tarball URL downloaded at install time, a git URL with an optional ref, GitHub shorthand with an optional commit, a local file path and an alias. For git URLs, the page notes that with no ref, npm uses the default branch.
That last detail is the main risk. A dependency pointing at a branch gets whatever is on that branch when someone installs.
Reading the diff
| Form in package.json | Risk | Ask for |
|---|---|---|
| Git URL, no ref | Follows the default branch | A commit hash |
| Git URL with a tag | Tags can be moved | A commit hash if the source is not trusted |
| GitHub shorthand with commit | Pinned, but source is a repo not a release | An owner check |
| Tarball URL | Remote file at install time | A reason, and an integrity check |
| Local path | Fine for development | Not in published packages |
Questions for the author
- Why is a registry release not enough? A bug fix not yet released is a fair answer. Convenience is not.
- Who owns the repository? A personal fork of a popular library is a very different thing from the maintainers' own repository.
- Is there a plan to move back to a registry version? Ask for a tracking issue.
- Is the commit pinned? Without it, two builds a week apart can differ.
- Does the lockfile record what was resolved? Check that the resolved commit appears in the lockfile diff.
{
"dependencies": {
"example-lib": "github:example-org/example-lib#4727d35"
}
}
The package and hash above are placeholders to show the shape.
Why this differs from a registry package
Registries give you named versions, publish history and tooling that checks advisories by name and version. A git dependency may not match advisory data cleanly, because the version string in the manifest might not correspond to a released number. Scanners and your inventory may then describe it poorly. Make sure the dependency still appears in your SBOM with something a person can trace.
If a fork is unavoidable, record in the pull request description who owns it, why it exists, and when it should be removed. That note is what the next reviewer will want.
Try it yourself
In the demo, find a dependency in the inventory and note what information is shown for it. Think about which of those fields would be missing for a git URL.
Click through it at your own pace, or open it full screen.
Where Safeguard fits
Safeguard scans dependencies and produces SBOMs so unusual sources show up in your inventory. Try the free scan at gold.safeguard.sh/scan.
Quick check
What does npm do with a git URL that has no ref?
It uses the default branch, so the code can change between installs.
Is a tag a good pin?
Only with trust in the owner. A commit hash is firmer.
Sources
Last reviewed: 19 October 2026.