Getting started contributing to Node.js

You guys, check this out. Most of node.js is just written in javascript.

The Dark Arts

That node.js is written in Javascript is such a banal platitude that I hadn’t really considered that I might be able to contribute to a thing that I use every day.

“…the most obvious, ubiquitous, important realities are often the ones that are hardest to see” — David Foster Wallace

Part of this comes from my natural, default assumption that node.js is a complex, opaque layer of black magic. Some cognitive shortcut led me to conclude — without really realizing — that, to contribute to node itself, I needed some deep and arcane PhD-grade wisdom. Reading the build instructions, the fact that I needed to compile something already looked scary.

Dive In

The other day, I ran across a strange issue with the Node REPL while building trailpack-repl. I’ve so far spent a few hours ambling through the source code to track down this bug, and I’ve discovered an obvious reality that most of node.js is just javascript.

Setting up the node project locally, and compiling it, could not have been easier. On OSX, it’s as simple as running these commands in the terminal

$ git clone
$ cd node
$ ./configure
$ make
$ make install

You may need to use “sudo” for the “make install” command.

Fix Something

The workflow for node.js development is likely similar to what you’re used to in other projects. After you make some changes, you can simply run

$ make test

to run the built-in test suite. For the issue I ran into, it looked like the close() logic for either REPL or Readline wasn’t working properly. If I stopped/started REPL more than once, behavior seemed to change, so it seemed plausible that REPL wasn’t cleaning up its resources properly.

I found myself looking and these pieces of code:


Interface.prototype.close = function() {
if (this.closed) return;
if (this.terminal) {
this.closed = true;


self.once('close', function() {
input.removeListener('keypress', onkeypress);
input.removeListener('end', ontermend);
if (output !== null && output !== undefined) {
output.removeListener('resize', onresize);


This code is fairly straightforward. In Interface.close, we set a flag “this.closed” to true, pause the readline interface so that it doesn’t listen to any more input, and the emit a “close” event. The constructor sets up the “close” listener, and inside it, other listeners are removed from the input and output streams.

While ostensibly “low-level”, much of the node.js code is quite readable and understandable. Keep this in mind next time you run into a strange issue. Dig into the code and see what you find.

One clap, two clap, three clap, forty?

By clapping more or less, you can signal to us which stories really stand out.