-
Notifications
You must be signed in to change notification settings - Fork 3.3k
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
fix: don't trash optional dependencies that fail due to incompatible platform #8127
base: latest
Are you sure you want to change the base?
Conversation
…n incompatible platform, to prevent issues when either the lockfile is removed
@wraithgar would you be able to take a look at this PR? Thanks 👍 |
@owlstronaut thanks for running the test suite. So, in this case, would it make sense to adjust the tests? Seems like these are incorrect, if we want to retain the entries in the lock file. About code coverage, where would i need to add or extend the tests for build-ideal-tree? See also #8127 (comment) |
Sure! Yeah, in this case we would need to update the snapshot for the new expectations from reify, and for the
I still have to leave your questions about the "right thing" to do open to @wraithgar, I've been on the team less than a month 😸 |
Working through the tests and comments now, hope to push something this evening. |
- fix tests by adjusting snapshots for reify, now that it doesn't trash optional dependencies that fail due to a platform mismatch - fix tests for isolated-mode by adjusting the assertions to not expect failure, but expect an empty directory though in case of a platform mismatch
@owlstronaut Could you run the test suite again? I fixed all the snapshot and failing tests. Besides, i removed the code in build-ideal-tree, as it never seems to hit (in unit tests, but also not when building locally). The code in build-ideal-tree is not entirely clear to me, as i cannot figure out if With these changes, the original issue is still verified to be fixed, see the changed snapshots. |
@@ -552,9 +552,10 @@ tap.test('failing optional deps are not installed', async t => { | |||
const arborist = new Arborist({ path: dir, registry, packumentCache: new Map(), cache }) | |||
await arborist.reify({ installStrategy: 'linked' }) | |||
|
|||
t.notOk(setupRequire(dir)('which'), 'Failing optional deps should not be installed') | |||
t.ok(setupRequire(dir)('which'), 'Failing optional deps should not be installed, but the empty directory is there') |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Am I right to say that the new behavior would be to leave empty directories for all of the optional deps that did not succeed? Hopefully there's a way to avoid this, since that would leave a load of empty dirs for a lot of native packages, and potentially confuse code which is scanning for these dirs to know which one to load for the current platform...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That is correct indeed. This is used to rebuild the proper package-json.lock file based on the node_modules
directory.
I don't know enough of NPM to surface a better solution, but maybe others have ideas on how this can prevented?
Instead of the empty directory, it could also keep a list of failed optionals in a separate file or something, but that would require far more changes i would assume.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That's really unfortunate; I thought that npm stored a file inside node_modules
that described the layout? It seems like a bad idea to rely on an empty dir existing, and I really do think it'll cause something to break.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, i can imagine breakage if packages rely on directory scanning without verifying the contents.
If this is not the desired approach, i would need guidance from the maintainers on what would be the best way forward.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yep, we'll have @wraithgar weigh in
This PR is a proposed solution for multiple reported issues regarding failed optional dependencies that are platform specific.
See #4828, #7961 and possibly related PR #8077.
It can be reproduced as follows:
mkdir test && cd test
npm init -y
npm i --verbose rollup
rm package-lock.json
npm i --verbose
With this PR, the
package-lock.json
will remain to contain the initial 18 rollup related dependencies, as any optional failure due to incompatible platform (EBADPLATFORM
) will not lead to trashing the node.The side-effect of this is that all platform specific dependencies will be present on all platforms (just an empty directory where the platform doesn't match). But it does solve the issue at hand.
I would need help writing a proper unit test for this scenario though. With the steps below, i did manage to test my PR and see that it has the desired effect:
node . i --verbose rollup
rm package-lock.json
node . i --verbose
It will show this in the logging (on my Windows based machine):