Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Avoid parsing dependency package.json's when searching for local bin to run #393

Closed
rwjblue opened this issue May 1, 2019 · 3 comments · Fixed by #420
Closed

Avoid parsing dependency package.json's when searching for local bin to run #393

rwjblue opened this issue May 1, 2019 · 3 comments · Fixed by #420
Assignees

Comments

@rwjblue
Copy link
Contributor

rwjblue commented May 1, 2019

Currently (my understanding) is that when a binary is installed at the user/global level (e.g. notion install ember-cli), and then a bin script is invoked (e.g. ember build) within a project we do the following:

  • Parse the project's own package.json
  • Iterate the projects dependencies/devDependencies (should also do optionalDependencies but I don't know if we do?)
  • Search each of those combined deps's package.json (e.g. node_modules/package-name/package.json) for bin scripts with the given name
  • If found, use the local bin
  • If not found, use the globally installed package's bin script

Having to open and parse all of the dependencies/devDependencies's package.json's adds additional overhead to launching, and I believe it can be avoided completely.

I propose:

  • Parse the project's own package.json
  • Look for the specific installed package (e.g. ember-cli from my example) in the dependencies/devDependencies
  • If found, use the local bin
  • If not found, use the globally installed package's bin script

This relies on the fact that we keep track of which package a given globally installed bin shim is provided by, so we can directly compare/look for that instead of manually searching.

Changing to this system would have a few benefits:

  • Lower overall overhead for globally installed shims
  • Better resilience to malformed package.json's (we no longer need to parse all of the dependencies/devDependencies package.json, only the projects itself and possibly the local installed version of the global package)
  • Better alignment with PnP (the manually parsing the node_modules tree will have to branch when in a PnP project vs when not in one, IMHO better to remove the branching)

This idea originally came from the discussion in discord when #388 was reported.

@rwjblue
Copy link
Contributor Author

rwjblue commented May 1, 2019

Definitely not conclusive evidence of anything specific, but it appears that the global shims today are adding a bit of overhead (more than I would have expected):

  • Average of 10 time ember version: 1.31s
  • Average of 10 time node_modules/.bin/ember: 1.1s

@rwjblue
Copy link
Contributor Author

rwjblue commented May 1, 2019

While poking at the performance differences I mentioned in my last comment, I decided to test what the impact is of having many dependencies/devDependencies while using the global shim.

When I delete all dependencies and devDependencies other than ember-cli, the there is no measurable time difference between time ember v and time node_modules/.bin/ember v.

tldr; the extra dependency traversal and package.json parsing is likely to be the cause of the slower performance of global shim binaries compared to directly invoking their project local bins.

@charlespierce
Copy link
Contributor

Out of curiosity, in the test you did above where there was a ~0.2s difference between the two invocations, how many dependencies did that project have?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants