To find which package pulled in a vulnerable dependency, read the dependency path in your SCA report, or ask your package manager. In npm, run npm explain with the package name. In Maven, print the dependency tree. Each shows the chain from your direct dependency down to the vulnerable library.
Why the path matters
Findings in an indirect (transitive) dependency are common, and you cannot fix them by editing the vulnerable package. You fix them by changing something above it in the chain. The path tells you what to change. Without it you are guessing.
The npm documentation describes npm explain as printing the chain of dependencies causing a given package to be installed in the current project. The command is also available under the alias why.
Reading a path
A path reads from top to bottom, your project first, the vulnerable library last.
my-app
web-framework 4.2.0 (direct)
request-helper 1.8.0 (indirect)
parser-lib 0.9.2 (vulnerable)
Here you cannot upgrade parser-lib directly in a clean way. You would upgrade web-framework, or request-helper if your manager allows an override.
Commands for common ecosystems
| Ecosystem | Command | What it shows |
|---|---|---|
| npm | npm explain package-name | Chain of dependents for the package |
| npm | npm ls package-name | Where the package sits in the installed tree |
| Maven | mvn dependency:tree | Full dependency tree |
| pip | pip show package-name | Package details, including what it requires |
The Maven dependency plugin documents that its tree goal displays the dependency tree for the project in text, DOT, GraphML, TGF and JSON formats. It also has a verbose option that includes nodes omitted from the tree, which helps when version conflict resolution hides the path you expected. The pip documentation says pip show displays information about installed packages.
Three outcomes after you read the path
- The vulnerable package is direct. Upgrade it to the fixed version.
- A direct package has a newer release that pulls a fixed version. Upgrade that parent.
- No parent release helps. Consider an override or resolution entry, a replacement package, or waiting for the maintainer, and record the decision.
The npm documentation also defines a "meta-vulnerability": a dependency that is vulnerable by virtue of depending on vulnerable versions of another package. That is why a report sometimes lists parents as vulnerable too. Fix the bottom of the chain and the parents clear.
Try it yourself
Click through it at your own pace, or open it full screen. Open a package and follow the chain to see which direct dependency introduced it.
Where Safeguard fits
Safeguard's dependency scanning shows the chain for each finding, and reachability analysis helps you judge whether the vulnerable code is used before you spend time on the parent upgrade.
Quick check
What is a transitive dependency?
It is a package your project does not list itself but receives because something you do list depends on it.
Why does the parent also appear as vulnerable?
npm calls this a meta-vulnerability: the parent is vulnerable only because it depends on a vulnerable version of another package.
Sources
- npm Docs, npm explain
- npm Docs, npm audit
- Apache Maven Dependency Plugin, dependency:tree
- pip documentation, pip show
Last reviewed: 19 October 2026.