This repository has been archived by the owner on Jul 3, 2019. It is now read-only.
Ensure that stream failures are sent up the promise chain #177
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
The problematic code prior to this PR is this:
There's a race condition in this code. The problem is that neither of the
tarStream.on('error', reject)
lines are capable of reporting all errors withtarStream
. If atarStream
error happens prior to the outerresolve
being called, then the firsttarStream.on('error'...
will pass the error up correctly. (Actually, I don't think this case is possible. At some point I had instrumented the callback passed to both calls totarStream.on('error'...
and the callback passed tosetImmediate(...)
, and it never ever ever ever ever happened that the firsttarStream.on('error'
caught an error prior to the call scheduled withsetImmediate
.)However, for those errors that cannot be detected immediately the first
tarStream.on('error'
call is useless. By the time these errors are raised, theresolve
call scheduled bysetImmediate
will have happened, and thus even if the firsttarStream.on('error'
callsreject
, this will have no effect whatsoever because the promise has already resolved.So there is a window of time between the first
tarStream.on('error'
and the second one where if atarStream
error occurs, it won't be sent up the promise chain. How big a window it is depends on how longrimraf
andmkdirp
take to do their work. If atarStream
error is raised during that window, the firsterror
event handler cannot do anything about it, and the 2nd event handler is not setup yet so it cannot do anything either.The test I created to test the issue changes
PATH
to an empty string temporarily so that executinggit
will fail. It replicates the problem I initially ran into: I was runningnpm
in a docker build wheregit
was not installed, and I got the utterly non-descriptivecb() never called
error message. (And nothing else. I've seen cases wherecb() never called
is accompanied with some more information but in my case that was the sole error message and--loglevel=silly
did not help either.)