Created

Embed URL

HTTPS clone URL

SSH clone URL

You can clone with HTTPS or SSH.

Download Gist

Node.js does not detect process.stdout pipe closing

View node-yes-simplistic.js
1 2 3 4 5 6
// this terminates: yes | head
// this hangs: node node-yes-simple.js | head
// per mhart, this is entirely expected
while(true) {
process.stdout.write('{"yes": "yes"}\n');
}
View node-yes-simplistic.js
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
// Keep saying yes until interrupted or someone closes your output pipe:
 
var running = true;
function say_yes() {
if (running) {
process.stdout.write('{"yes": "yes"}\n');
process.nextTick(say_yes);
} else {
process.exit(0);
}
}
 
process.stdout.on('error', function(err) {
running = false;
if (err.code === 'EPIPE') {
// expected if output pipe closed, e.g. by `head`
process.exit(0);
} else {
process.stderr.write(JSON.stringify(err) + '\n');
process.exit(1);
}
});
Owner

Spotted while testing Trent's pipe solution for jsontool. Michael Hart is still getting EPIPE error events, though, hence epipebomb.

You're starving the event loop with the infinite while.

Try this:

function writeYes() {
  process.stdout.write('{"yes": "yes"}\n');
  process.nextTick(writeYes);
}
writeYes();

(NB: The difference with the example in epipebomb is that the process there actually terminates so the events are processed after the for loop finishes - it's not infinite like the while examples here)

Owner

Updated. Thanks!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Something went wrong with that request. Please try again.