48

Github has flagged a dependency in my app lock file as vulnerable.

To fix it I should updated that package to a newer version.

How do I do that if I don't have any control on the vulnerable package, because is nested in the dependencies tree?

Apologies if this is a very basic question but I don't seem to find anything useful regarding this.

U r s u s
  • 6,680
  • 12
  • 50
  • 88
  • Does this answer your question? [How do I fix a vulnerable npm package in my package-lock.json that isn't listed in the package.json?](https://stackoverflow.com/questions/50328324/how-do-i-fix-a-vulnerable-npm-package-in-my-package-lock-json-that-isnt-listed) – JBallin Feb 01 '20 at 00:29
  • https://www.npmjs.com/package/npm-force-resolutions or `npm shrinkwrap`. they basically do the same thing but the first is more convenient to use. – Paolo Feb 09 '21 at 00:48
  • Does this answer your question? [How do I override nested NPM dependency versions?](https://stackoverflow.com/questions/15806152/how-do-i-override-nested-npm-dependency-versions) – Henke Apr 06 '23 at 13:27

6 Answers6

15

NPM 8 introduced "overrides" to help workaround these type of issues. You can now override specific transitive dependencies of your direct dependency to the version you need. In your case, you would declare something like below to fix the vulnerable dependency.

{
  "overrides": {
    "your-direct-dependency": {
      "vulnerable-package": "fixed_version"
    }
  }
}

More details @ https://docs.npmjs.com/cli/v8/configuring-npm/package-json#overrides

Sateesh
  • 735
  • 8
  • 10
  • This requires NPM 8.3 minimum. I like the idea, and good answer @Sateesh, but it does not seem particularly reliable. There's a GitHub issue that has a lot of people complaining that it doesn't work, and the dev team just closed it without fixing the issue. https://github.com/npm/cli/issues/4232. I tried to use this answer, but I had the same problem as everyone else in this issue, and none of the suggestions worked for me. – Mark Jan 24 '23 at 09:59
13

You're correct - as the vulnerable package lies within one of your dependencies, like so:

Your Package -> Dependency -> Vulnerable package

You will be unable to update the dependencies' dependency in a way that would survive a future npm install or yarn.

However, you could take the following approaches:

  • Bug the maintainer: Get them to update their dependencies and bump versions. This will fix the issue for you and your peers who are depending on this package.
  • Are there alternative packages? Maybe you can use a different package instead of the vulnerable one. This will involve some updates to your code, but might be the best approach in the long run, especially if the original maintainer is unresponsive.
  • Fix it yourself: Fork the repository and update the dependency in this copy. You can then refer to the package in your package.json.

See this answer for more information on installing directly from Github repos.

This approach will fix the problem short term, but it is not advised as you won't benefit from any bug fixes the maintainer makes, and besides, by the time you've done this the dependency might have been updated anyway!

Tom Hallam
  • 1,924
  • 16
  • 24
3

I think there is a way to (potentially) achieve this with the depth flag.

caveat 1: The official npm update documentation advices to use a depth of 9999 to recursively inspect all dependencies. But on my setup that either results in an error or npm freezing. So I use a realistic depth of 1 or 2. (0 is the default, meaning only direct dependencies)

UPDATE: See mike's comment below. The depth option is no longer supported; npm update <name> will now update all instances of name in the tree, except those in a bundled or shrinkwrapped tree.

So this should still work:

npm update vulnerable_package

caveat: This only works if there is an updated version available of the nested package (with a fix for the vulnerability) that still fits the version range of your dependency. So if this is your dependency tree:

Your Package -> Dependency@^1.0.0 -> Vulnerable_package@^2.1.0

And the vulnerability fix is in Vulnerable_package version 3.0.0, then it won't work, since npm update will only update to the highest version that still fits the version range of your dependency. (in this case the highest 2.x.x release)

gijswijs
  • 1,958
  • 19
  • 24
  • 1
    npm WARN update The --depth option no longer has any effect. See RFC0019. – mike Mar 05 '21 at 21:41
  • I believe that RFC was implemented in npm v7, so if you're still stuck on npm <= 6 you'll need `--depth` still I think, – Zach Lysobey Feb 04 '22 at 16:28
  • 1
    @ZachLysobey I think you are right, but even in v6 the behavior is erratic depending on the minor version you are using. See: https://github.com/npm/cli/pull/239 – gijswijs Feb 07 '22 at 00:21
2

As explained here: https://stackoverflow.com/a/17423915, you can use npm shrinkwrap to explicitly tell npm to get the nested dependency version that you want.

Julien
  • 953
  • 9
  • 15
0

Adding the nested dependency directly in the package.json file with updated version worked for me. It updated the nested package versions also.

Eric Aya
  • 69,473
  • 35
  • 181
  • 253
-8

First Update command
npm install -g npm

then, to remove vulnerable

npm audit fix --force