How do I programmatically shut down an instance of ExpressJS for testing?

Things have changed because the express server no longer inherits from the node http server. Fortunately, app.listen returns the server instance.

var server = app.listen(3000);

// listen for an event
var handler = function() {
  server.close();
};

Use app.close(). Full example:

var app = require('express').createServer();
app.get('/', function(req, res){
  res.send('hello world');
});
app.get('/quit', function(req,res) {
  res.send('closing..');
  app.close();
});
app.listen(3000);

Call app.close() inside the callback when tests have ended. But remember that the process is still running(though it is not listening anymore).

If after this, you need to end the process, then call process.exit(0).

Links:

app.close: http://nodejs.org/docs/latest/api/http.html#server.close (same applies for)

process.exit: http://nodejs.org/docs/latest/api/process.html#process.exit


I have answered a variation of "how to terminate a HTTP server" many times on different node.js support channels. Unfortunately, I couldn't recommend any of the existing libraries because they are lacking in one or another way. I have since put together a package that (I believe) is handling all the cases expected of graceful HTTP server termination.

https://github.com/gajus/http-terminator

The main benefit of http-terminator is that:

  • it does not monkey-patch Node.js API
  • it immediately destroys all sockets without an attached HTTP request
  • it allows graceful timeout to sockets with ongoing HTTP requests
  • it properly handles HTTPS connections
  • it informs connections using keep-alive that server is shutting down by setting a connection: close header
  • it does not terminate the Node.js process

Usage with Express.js:

import express from 'express';
import {
  createHttpTerminator,
} from 'http-terminator';

const app = express();

const server = app.listen();

const httpTerminator = createHttpTerminator({
  server,
});

await httpTerminator.terminate();