Force flush headers using the HTTP module for NodeJS

Although it’s not something that you’ll commonly want to do, today I found myself wanting to flush HTTP headers immediately without sending any additional data with them. Internally, NodeJS won’t send headers until it needs to. For most applications, this is when the first bit of data is sent.

After judicious use of grep, I came across the HTTP outgoing lib file, which contained all the information I needed to force node to flush the headers. You need to use writeHead to build up your headers, and then you can access the header string in response._header. Then, you write it to the socket using response.socket.write (or if you prefer, you can use response._writeRaw), and finally you mark that headers have already been sent so that if anything uses response.write in the future you won’t get the headers sent twice (which gives the following, awesome error message: “Received problem 2 in the chunky parser”)

So, the actual code:

// This will build the HTTP response to send back headers
response.writeHead(200, {
  'Connection': 'keep-alive',
  'Content-Type': 'application/json; charset=utf-8',
  'Transfer-Encoding': 'chunked'
});

// Write the headers to the socket
response.socket.write(response._header);
// Mark the headers as sent
response._headerSent = true;

Michael is a polyglot software engineer, committed to reducing complexity in systems and making them more predictable. Working with a variety of languages and tools, he shares his technical expertise to audiences all around the world at user groups and conferences. You can follow @mheap on Twitter

Thoughts on this post

Max Aller 2013-10-27

Interesting to know there’s this possibility, but…I’m just going to do req.write(“\n”, ‘utf8’); instead. Less likely to break in the future.

michael 2013-11-06

Yeah, if you can use req.write(), go for it.

In this specific case, we couldn’t send *any* data to the client unless it was a piece of valid customer data. Unfortunately, we also needed to communicate which node they connected to immediately (via headers), so this was the only solution.

Leave a comment?

Leave a Reply