From 69a2a6b6c3a46e8daac952dc7bfb9e404b6293bd Mon Sep 17 00:00:00 2001 From: Matteo Collina Date: Fri, 6 Aug 2021 13:01:58 +0200 Subject: [PATCH] bootstrap: call _undestroy() inside _destroy for stdout and stderr This change makes `process.stdout` and `process.stderr` to be automatically undestroyed when ended/destrouyed, therefore making it always possible to write/console.log to stdout. Fixes: https://github.com/nodejs/node/issues/39447 PR-URL: https://github.com/nodejs/node/pull/39685 Reviewed-By: Robert Nagy Reviewed-By: Anna Henningsen Reviewed-By: Ruben Bridgewater Reviewed-By: Joyee Cheung --- .../bootstrap/switches/is_main_thread.js | 1 + test/parallel/test-stdio-undestroy.js | 36 +++++++++++++++++++ 2 files changed, 37 insertions(+) create mode 100644 test/parallel/test-stdio-undestroy.js diff --git a/lib/internal/bootstrap/switches/is_main_thread.js b/lib/internal/bootstrap/switches/is_main_thread.js index 08623898edafac..1885f79ffec09e 100644 --- a/lib/internal/bootstrap/switches/is_main_thread.js +++ b/lib/internal/bootstrap/switches/is_main_thread.js @@ -100,6 +100,7 @@ function createWritableStdioStream(fd) { function dummyDestroy(err, cb) { cb(err); + this._undestroy(); // We need to emit 'close' anyway so that the closing // of the stream is observable. We just make sure we diff --git a/test/parallel/test-stdio-undestroy.js b/test/parallel/test-stdio-undestroy.js new file mode 100644 index 00000000000000..b525672db27c5a --- /dev/null +++ b/test/parallel/test-stdio-undestroy.js @@ -0,0 +1,36 @@ +'use strict'; +const common = require('../common'); +const assert = require('assert'); +const spawn = require('child_process').spawn; + +if (process.argv[2] === 'child') { + process.stdout.destroy(); + process.stderr.destroy(); + console.log('stdout'); + process.stdout.write('rocks\n'); + console.error('stderr'); + setTimeout(function() { + process.stderr.write('rocks too\n'); + }, 10); + return; +} + +const proc = spawn(process.execPath, [__filename, 'child'], { stdio: 'pipe' }); + +let stdout = ''; +proc.stdout.setEncoding('utf8'); +proc.stdout.on('data', common.mustCallAtLeast(function(chunk) { + stdout += chunk; +}, 1)); + +let stderr = ''; +proc.stderr.setEncoding('utf8'); +proc.stderr.on('data', common.mustCallAtLeast(function(chunk) { + stderr += chunk; +}, 1)); + +proc.on('exit', common.mustCall(function(exitCode) { + assert.strictEqual(exitCode, 0); + assert.strictEqual(stdout, 'stdout\nrocks\n'); + assert.strictEqual(stderr, 'stderr\nrocks too\n'); +}));