npm link does not care for "files" in package.json or .npmignore

3.9k views Asked by At

My goal is to specify what files will be included in my node module before publishing it and be able to test the installation locally. Using the "files" in the package.json works in that if I publish my package and install it, then I get only what was specified in "files".

This isn't the case when I use npm link. Be it "files" in package.json or an .npmignore, npm link always seems to give me every file. How can I test my modules installation locally like this?

Ex:

cd ~/projects/node-redis    # go into the package directory
npm link                    # creates global link
cd ~/projects/node-bloggy   # go into some other package directory.
npm link redis              # link-install the package

If ~/projects/node-redis had "files: [lib]" in its package.json, you would expect only lib to show up in ~/projects/node-bloggy after running "npm link redis", but this is not the case.

Aside: I love node and npm, but if you look at what is in your node modules, there's so many extraneous files like PNGs used in the readme. Modules are ridiculously huge because of this.

UPDATE:

npm install <path>

seems to respect "files" in package.json according to an answer here and others on stackoverflow. I can't speak for other systems but with npm v 6.9.0 on Fedora Linux, this doesn't work as all files are still copied.

Example:

If you need a published module to test this scenario with, I recently published num2cheque which has no dependencies. You will see that if you install it from the npm registry with

npm install num2cheque

you do not receive the test directory which I have locally because in the package.json I specify

"files": [lib]

Add a test directory to your local install then try to use npm link or npm install with a path and you will see that test directory is now included. Hope that illustrates the issue.

1

There are 1 answers

5
AndreasPizsa On BEST ANSWER

Workaround: npm install a GIT repo URL

You may want to install a package from a GIT repo, eg

npm install https://github.com/AndreasPizsa/parse-decimal-number.git

This is an actual npm install which respects the files entry, even if the package has not yet been published to an npm repository.


Background

npm link does not copy, it creates a link

npm link does not actually install the package by copying it into the target folder.

Instead it creates a symbolic link to the source folder, which is why you’re seeing all the files that are in the source folder ("node-redis"), not just those specified in files.

This behavior is documented in the npm link documentation:

First, npm link in a package folder will create a symlink in the global folder {prefix}/lib/node_modules/ that links to the package where the npm link command was executed. (see npm-config for the value of prefix). It will also link any bins in the package to {prefix}/bin/{name}.

Next, in some other location, npm link package-name will create a symbolic link from globally-installed package-name to node_modules/ of the current folder.

https://docs.npmjs.com/cli/link.html

"What’s a Symlink?" you may ask:

a symbolic link (also symlink or soft link) is a term for any file that contains a reference to another file or directory in the form of an absolute or relative path and that affects pathname resolution.

https://en.wikipedia.org/wiki/Symbolic_link

If your concern is the use of space on your hard disk, worry not - nothing is copied or duplicated, only linked (just like linking to Wikipedia doesn’t duplicate it, it actually saves space)

... and so does running npm install locally

npm install with the path to the package will also create a symbolic link to the package in question. A helpful scenario for this can be a module that’s still under development.

cd ~/projects/node-bloggy
npm install ~/projects/node-redis

This will create a symbolic link under node_modules in your node-bloggy project.