Skip to content
This repository was archived by the owner on Aug 11, 2022. It is now read-only.

Conversation

@watilde
Copy link
Contributor

@watilde watilde commented Nov 10, 2016

From here #6756 (comment)

this screenshot was updated with current progress at 4th December 2016
screenshot

ToDo:

  • Add new subcommand
  • Write a test
  • Replace getLatestNodejsVersion with a fixturable way
  • Update docs

@legodude17
Copy link
Contributor

Does this add any new deps?

lib/doctor.js Outdated
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Wouldn't it be 'npm@' + npmV?

@othiym23
Copy link
Contributor

@watilde I owe you a response! I'll try to get to it today! The summary is this looks fantastic, but we need to talk a lil more about the functionality everybody wants.

@legodude17
Copy link
Contributor

Current comments:

  • Any ideas on a more exhaustive test then, "It prints things out with 5 lines"? I was thinking maybe make sure it prints a table and that the columns match.
  • What is the best way to get the latest node version? I think that yours is the best way.

@watilde
Copy link
Contributor Author

watilde commented Nov 15, 2016

@legodude17 Yes, that's a good point. Before that, I'm thinking about a way to make the test having a fixture in test.

@othiym23 Sure thing! Let's continue the discussion at #6756

@watilde watilde force-pushed the feature/doctor-wombat branch from 1b49329 to 6333bc7 Compare November 19, 2016 06:50
@watilde watilde changed the title [WIP] Add new subcommand npm doctor Add new subcommand npm doctor Nov 20, 2016
@legodude17
Copy link
Contributor

@watilde is this still in-progress?

@watilde
Copy link
Contributor Author

watilde commented Nov 21, 2016

@legodude17 It's fixed technically for the original plan, but the code potentially will be changed depending on what kind of request comes from the issue thread. Then the status doesn't matter anymore :)

@legodude17
Copy link
Contributor

One suggestion from #6756 is to offer to fix it like Would you like me to run npm cache clean for you?. I think that would be great, but maybe in a separate PR.

Copy link
Contributor

@othiym23 othiym23 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@watilde, my apologies for the lengthy delay. It's been a bruiser of a month.

Here, in no particular order, are my thoughts:

  1. I'm not in love with the idea of prescribing that users nuke their caches every time they run npm doctor. It makes installs (potentially much) slower until the cache rewarms, and in cases in which the user is on a flaky internet connection, can actually make installs even flakier. If at all possible, I'd like to move to advising people to only npm cache clean individual broken dependencies.

    It's probably out of scope for this initial spike, but something that validates that the cache is in good shape (and maybe went ahead and cleaned up any shasum mismatches automatically) would be a super useful alternative.

  2. Something that validates that $HOME/.npm and all its children is owned and writable by $USER would be very helpful for diagnostic purposes.

  3. Similarly, something that checks whether join(npm.config.globalPrefix, 'lib', 'node_modules') is writable and tells the user whether they need to use sudo to run global installs would be very helpful.

  4. It would be very helpful to verify that Git is installed and available, especially for Windows users.

  5. This is another thing that doesn't have to be added yet, but something that builds a very simple canned native module with node-gyp would be extremely helpful for Windows users unsure whether they have their toolchain correctly installed.

  6. Finally, and longest-term, it would be fantastic to have some way for npm to verify its own integrity, which probably requires that some kind of install manifest be generated for it. While it would be useful to have this functionality for npm packages in general, it's especially important for npm, because of the Node.js installer's bad habit of just copying the new npm right over the top of the old one, which causes a bunch of the stranger module not found bugs that show up on the issue tracker. Being able to catch this automatically would be hugely useful.

This is basically my wishlist, though. What you've got is a fantastic start, and when you get the above comments addressed, I'll ship what you've got so far. Thank you so much for putting this together!

lib/doctor.js Outdated
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You're going to want to use a semver range comparator here, because something weird will happen as soon as Node 10 is released. 👍 on the check for LTS, though – that's exactly what I was looking for.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should be expanded to explain all of the questions and answers, as well as the team's consensus about rationales for the recommendations.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It would be cool if npm doctor produced output in a format similar enough to Markdown that the output could just be cut and pasted directly into a new issue.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think the best way to do that would be to template it, but I am not sure about what anyone's thoughts are about including a template engine with npm.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's absolutly good idea, and I'd like to have the feature in npm report command which have been proposaling at #5214. I'm planning to use the ISSUE_TEMPLATE.md as a acutual template, but let's separete the reporting part from this diagnosis part to make the initial scope clear and simple.

lib/doctor.js Outdated
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A lot of these aren't really questions, so I suggest something like Check, Value, and Recommendation.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good point @othiym23.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

True! I've updated :)

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shouldn't this use the url initialized above?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's right! I've updated.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The test should verify that npm doctor is producing sensible output, and should also start up a mock registry that allows the test to control which version of npm is returned.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah it should be since npm doctor ask the things to the registry through npm ping and fetchPackageMetadata. I've added npm-registry-mock into this test and verifying all of the output!

lib/doctor.js Outdated
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd prefer this to pull d['dist-tags'].latest instead, so that npm doctor always recommends latest instead of next.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So cb(er, d['dist-tags'].latest)?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've updated with npm@latest check.

lib/doctor.js Outdated
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good call.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

...but this is part of why we need to be matching against npm doctor actually returns in the tests, because it seems very possible to me that changes made to the configuration code could break this command without anyone noticing otherwise.

Copy link
Contributor Author

@watilde watilde Dec 4, 2016

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added it to the test! Once the structure of default properties are changed, the test makes an error.

@watilde
Copy link
Contributor Author

watilde commented Dec 1, 2016

@othiym23 Hey Forrest, thanks for your thoughtful wish list! I'd like to separate examination processes and auto-fix features and let me reply to every wish-item of yours.

  1. Agreed! This request is the rest of the things I'd like to put into this PR.
  2. I've added into this PR already.
  3. I've added into this PR already.
  4. I've added into this PR already.
  5. I'd like to have node-gyp doctor instead of putting into npm doctor. Let's take out this from the current initial scope.
  6. This request may make this PR turning into a giant case of scope creep like you said. Could we also take out this from the current initial scope?

Additionally, I've added one more permission check for join(npm.config.localPrefix, 'lib', 'node_modules') since I was missing! As the initial plan to iterate from it, let's start with the following check-list as the smallest subset of information necessary to improve the supportability of npm.

  1. npm ping
  2. npm -v
  3. node -v
  4. npm config get registry
  5. which git
  6. Perms check on cached files
  7. Perms check on join(npm.config.globalPrefix, 'lib', 'node_modules')
  8. Perms check on join(npm.config.localPrefix, 'lib', 'node_modules')
  9. Shasum check for cached packages

Let me ping you when they're ready.

@legodude17
Copy link
Contributor

Some random ideas for things to add:

  1. Ensure the proxy is setup correctly (somehow)
  2. Ensure git is present and works

Keep up the great work @watilde!

@watilde watilde force-pushed the feature/doctor-wombat branch from fe36ada to 86b0824 Compare December 4, 2016 16:47
@watilde
Copy link
Contributor Author

watilde commented Dec 4, 2016

@othiym23 I've added some check items that I wrote down at #14582 (comment), and also written up the detailed documentation for the npm doctor command! Could I possibly request your review again?

(๑˃̵ᴗ˂̵)و let me cc to you as well @zkat

This command will diagnose user's environment and let
the user know some recommended solutions if they
potentially have any problems related to npm.
@watilde watilde force-pushed the feature/doctor-wombat branch from c9002da to d8b1b45 Compare December 7, 2016 20:39
@othiym23
Copy link
Contributor

I think this will be ready in time to include in this week's release, which might end up being the last release of the CLI in 2016! I only have a few further comments:

  1. Right now, the command seems to hang while it's running (I'm going to guess most of that is due to checking the shasums in the cache). If you add a log statement to each check at loglevel info and enable the progress bar, this will let users know that in fact something is happening.
  2. Because validating the hashes can be very time-consuming if people have a lot of packages in their cache, it might make sense to log at level debug each shasum you're validating, especially because you're doing so synchronously. Because the completion routine returns the number of files to check, it should be pretty easy to set up a progress group that will track the process of validating the cache. (This is a nice to have, and if it turns out to be tricky, don't worry about it and somebody can add it in later.)
  3. In the next day or two, I'll make a pass at expanding the docs you've written thus far, and make sure they'll tie in nicely with the the new TROUBLESHOOTING.md that @snopeks and @zkat are in the process of assembling.

This is really great! I can't wait to get it out into people's hands. Thank you so much for your patience and careful work, Daijiro!

@iarna iarna added this to the next milestone Dec 12, 2016
lib/doctor.js Outdated
var nodeLTS = p[2].replace('v', '')
var whichGit = p[3] || 'not installed'
var readbleCaches = p[4] ? 'ok' : 'notOk'
var executableGlobalModules = p[4] ? 'ok' : 'notOk'
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shouldn't these from this line down be 5, 6 & 7?

if (!/.tgz$/.test(file)) return
var tgz = fs.readFileSync(file)
try {
var pkgJSON = fs.readFileSync(path.join(file, '../package/package.json'))
Copy link
Contributor

@iarna iarna Dec 14, 2016

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think what's wanted here is: path.join(path.dirname(file), 'package/package.json')

Alternatively, I think: path.resolve(file, '../package/package.json')

Would have worked, but it's sufficiently weird that I prefer the former.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It also turns out that it's entirely ok for the package.json to be missing, in which case we ought to skip trying to verify the shasum.

var tgz = fs.readFileSync(file)
try {
var pkgJSON = fs.readFileSync(path.join(file, '../package/package.json'))
var shasum = JSON.parse(pkgJSON).dist.shasum
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

dist is added by the registry and won't be present for modules installed from other sources. _shasum should be available however.


function checkFilesPermission (root, mask, cb) {
var accessible = true
if (process.platform === 'win32') return cb(null, !accessible)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should probably be calling back with true shouldn't it? We don't want it to mark windows as always failing right?

files.some(function (f) {
if (!accessible) return true
var file = path.join(root, f)
fs.stat(file, function (e, stat) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fs.stat is async and files.some is sync, they can't be used together.

var getUid = require('uid-number')
var npm = require('../npm.js')

function checkFilesPermission (root, mask, cb) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

mask isn't being used like a umask which I think is the cause of an issue in how this function is being called…

lib/doctor.js Outdated
[getLatestNpmVersion],
[getLatestNodejsVersion, args['node-url']],
[which, 'git'],
[checkFilesPermission, npm.cache, 4],
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

filemode & 0400 would be true for files you have read access to. Should this be rewrite instead? (6)

lib/doctor.js Outdated
[getLatestNodejsVersion, args['node-url']],
[which, 'git'],
[checkFilesPermission, npm.cache, 4],
[checkFilesPermission, globalNodeModules, 1],
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

filemode & 0100 is true if you have execute access to. I'm assuming that this is supposed to be checking for read access? (4)

@iarna
Copy link
Contributor

iarna commented Dec 14, 2016

I put together a little patch that fixes the bugs that I encountered and reworks things to allow progress bars. You can see that here:

9fc0704

@watilde
Copy link
Contributor Author

watilde commented Dec 14, 2016

@iarna Thanks for your comments, and your patch seems so brilliant.. Let me do cherry-pick it into this PR, or you also can handle the commits to be suited for next-release.

iarna pushed a commit that referenced this pull request Dec 15, 2016
Credit: @watilde
Reviewed-By: @othiym23
Reviewed-By: @iarna
PR-URL: #14582
Fixes: #6756
iarna pushed a commit that referenced this pull request Dec 15, 2016
This command will diagnose user's environment and let
the user know some recommended solutions if they
potentially have any problems related to npm.

Credit: @watilde
Reviewed-By: @othiym23
Reviewed-By: @iarna
PR-URL: #14582
Fixes: #6756
@reconbot reconbot mentioned this pull request Dec 16, 2016
@iarna
Copy link
Contributor

iarna commented Dec 16, 2016

Thanks again for this! It was merged and released in 4.1.0.

@iarna iarna closed this Dec 16, 2016
@watilde watilde deleted the feature/doctor-wombat branch December 16, 2016 23:53
@zkat zkat mentioned this pull request Jan 26, 2017
4 tasks
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants