Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to force npm to flatten dependencies?

I have a project in which several frontends sharing a common lib.

The module dependencies of those projects are managed by npm.

So, in the package.json of each of those projects I have :

  "dependencies": {
    "mylib": "file:../<...path...>/mylib",
    ...other deps...
  },

I use "mylib" for two purposes :

  • share some classes ;
  • share common dependencies (mostly, angular)

Until now, I was using npm 3.3.12 and after running npm install, the angular dependencies of mylib where right under the node_modules directory of my top level projects.

So, I had for instance

node_modules
    @angular
        core
        common
        ....
    mylib

Now, with npm 5.4.2, I have :

node_modules
    mylib
        node_modules
            @angular
                core
                common

This causes a lot of problems in my build process.It requires additional configuration of typescript, by adding directives such as :

"baseUrl": "",
"paths": {
    "@angular/common": ["node_modules/mylib/node_modules/@angular/common/"],
    "@angular/core": ["node_modules/mylib/node_modules/@angular/core/"],
    "@angular/compiler": ["node_modules/mylib/node_modules/@angular/compiler/"],
    "@angular/compiler-cli": ["node_modules/mylib/node_modules/@angular/compiler-cli/"],
    "@angular/forms": ["node_modules/mylib/node_modules/@angular/forms/"],
    "@angular/http": ["node_modules/mylib/node_modules/@angular/http/"],
    "@angular/platform-browser": ["node_modules/mylib/node_modules/@angular/platform-browser/"],
    "@angular/platform-browser/animations": ["node_modules/mylib/node_modules/@angular/platform-browser/animations/"],
    "@angular/platform-browser-dynamic": ["node_modules/mylib/node_modules/@angular/platform-browser-dynamic/"],
    "@angular/router": ["node_modules/mylib/node_modules/@angular/router/"],
    "primeng/primeng": ["node_modules/mylib/node_modules/primeng/primeng"],
    "rxjs/Rx": ["node_modules/mylib/node_modules/rxjs/Rx"]
    }

in tsconfig.json

It becomes really annoying when you have to do similar configurations for AOT, rollup, etc...

I tried to use npm dedupe do simplify this. As the projects have a lot of dependencies, it takes over 10mn for just one of them :

npm dedupe
...
...
removed 824 packages and moved 1020 packages in 623.196s

Is there a standard, efficient way to have the same kind of dependencies flattening as before ? npm dedupe does the job, but takes so much time that it is not an acceptable alternative.

like image 758
Ludovic Pénet Avatar asked Oct 03 '17 09:10

Ludovic Pénet


People also ask

What does Deduped mean in npm?

deduped is short for "deduplicated" (duplicates were removed). The documentation for npm dedupe explains how npm does this: Searches the local package tree and attempts to simplify the overall structure by moving dependencies further up the tree, where they can be more effectively shared by multiple dependent packages.

What does npm prune -- production do?

If the --production flag is specified or the NODE_ENV environment variable is set to production , this command will remove the packages specified in your devDependencies .


1 Answers

As an alternative to npm you might want to switch to using yarn. That should dedupe modules by default. Start by removing your existing node_modules folder then just do yarn install.

You can also force yarn to do a flat install (yarn install --flat), but in this case it may be sufficient just to do the plain install.

Add the yarn.lock file to version control and any other checkout will then be locked down to the same module versions (unless they do yarn upgrade).

like image 98
Duncan Avatar answered Oct 12 '22 23:10

Duncan