diff --git a/lib/_stream_readable.js b/lib/_stream_readable.js index 996a14ddc0dc7d..5d2300cf891bca 100644 --- a/lib/_stream_readable.js +++ b/lib/_stream_readable.js @@ -777,8 +777,13 @@ Readable.prototype.pipe = function(dest, pipeOpts) { debug('onerror', er); unpipe(); dest.removeListener('error', onerror); - if (EE.listenerCount(dest, 'error') === 0) - errorOrDestroy(dest, er); + if (EE.listenerCount(dest, 'error') === 0) { + if (!dest.destroyed) { + errorOrDestroy(dest, er); + } else { + dest.emit('error', er); + } + } } // Make sure our error handler is attached before userland ones. diff --git a/test/parallel/test-stream-pipe-error-unhandled.js b/test/parallel/test-stream-pipe-error-unhandled.js new file mode 100644 index 00000000000000..42c1ce77fe4878 --- /dev/null +++ b/test/parallel/test-stream-pipe-error-unhandled.js @@ -0,0 +1,21 @@ +'use strict'; +const common = require('../common'); +const assert = require('assert'); +const { Readable, Writable } = require('stream'); + +process.on('uncaughtException', common.mustCall((err) => { + assert.strictEqual(err.message, 'asd'); +})); + +const r = new Readable({ + read() { + this.push('asd'); + } +}); +const w = new Writable({ + autoDestroy: true, + write() {} +}); + +r.pipe(w); +w.destroy(new Error('asd'));