Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to make sure NodeJS recovers after bad requests?

I was running a NodeJS app with Express 4, Mongoose, and MongoDB. Then I got a possibly bot GET request to which the response was 404. Usually the app carries on after that no problem, but this time it looked like it froze or stalled. And no page would load in my browser although the app was still technically running. It came back to normal after restarting.

After testproxy.php it would just emit half empty lines.

I know there is forever module that would restart your app if it crashes, not sure it would've been helpful in this case.

enter image description here

EDIT:

In my app.js (I was in dev mode):

app.use(function(req, res, next) {
  var err = new Error('Not Found');
  err.status = 404;
  next(err);
});

if (app.get('env') === 'development') {
  app.use(function(err, req, res, next) {
    res.status(err.status || 500);
    res.render('error', {
      message: err.message,
      error: err
    });
  });
}

It should've printed 500 Error, but it didn't because it thought it handled the 404 error and I don't think next(err) was ever fired in this case.

like image 837
ed-ta Avatar asked Nov 09 '22 18:11

ed-ta


1 Answers

Usually to fix that you really need to have some foreground (e.g. nodemon) or background (e.g. forever) daemon process which will take care your server crashes and restart your node instance.

The other important thing you need to take care is to kill process as soon as it's in undefined state.

For example you could add following middleware:

var serverProcess;

app.use(function(err, req, res, next) {
   // regular errors handler here
   // process further middleware if error can't be handled in the correct way
   next(err);       
});

app.use(function(err, req, res, next) {      
  // close request connection
  req.connection.end();

  // stop server process
  serverProcess.close(function() {      
    //An unhandled exception means your application is in an undefined state.
    //Blindly resuming means anything could happen.
    process.exit(1);
  });      
});

serverProcess = http.listen(httpPort, callback);

You can provide any other logic for killing your process, but keep in mind that something outside your application should handle this situation and restart your server properly.

like image 186
oleh.meleshko Avatar answered Nov 15 '22 05:11

oleh.meleshko