zackyang000 / node-odata

A library for easily create OData REST API, abide by OData protocol.
http://zackyang000.github.io/node-odata/en/
MIT License
365 stars 65 forks source link

Robustness: provide error handling when not able to connect #62

Closed mauriceKA closed 8 years ago

mauriceKA commented 8 years ago

Hello,

my use case is to make connection to MongoDB more reliable. I want my service to try to re-connect when the server is not available until it becomes available.

I tried wrapping the connection command var server = odata(mongoURI); in a try-catch block, but node still exits with a ECONNREFUSED exception.

Then, I looked whether there is a call-back to catch errors, like

var server = odata(mongoURI).on("error", function() {
   console.log("error");
});

but there is not.

Is there any way of handling a connection error and trying again later? If so, could you please document it?

By the way, wouldn't it be good to have one callback like in Mongoose, that accepts an error and a server parameter:

odata(mongoURI, function(err, server) {
   console.log("error");
});

Just returning the server reference synchronously is quite an unexpected API.

zackyang000 commented 8 years ago

Hi @mauriceKA,

Sorry, there is no way to detect db connect already break, I think the only solution is restart it until this version.

I will try to automatic re-connection when it available again in future version.

mauriceKA commented 8 years ago

My current work-around is like this: I try to connect with the plain MongoDB driver, which offers error handling, and only if I can reach the server, I proceed with the node-odata:

...
var odata = require("node-odata");
var MongoClient = require("mongodb").MongoClient

var connect = function () { 
    MongoClient.connect(mongoURI, function(err, db) {
        if (err) {
            setTimeout(connect, retryTimeout);
            return;
        }

        // from here on, mongo is reachable
        // starting odata server
        var server = odata(mongoURI);
    ...
    }
}

I would actually prefer, if you could offer a call-back like the plain Mongo driver instead of automatic re-connection. This would allow the library user to decide what to do on connection failures.

Alternatively, the lib reference could be an event source:

var odata = require("node-odata");
odata(mongoURI);
odata.on("connect", func);
odata.on("disconnect", func);
odata.on("error", func);

This would IMHO be the most elegant solution.

zackyang000 commented 8 years ago

Interesting point.

In my solution, the program will not received any notification when DB is failures.

You are right, we should offer as follows callback to let program know that.

odata.on("connect", func);
odata.on("disconnect", func);

Also, it will be automatic re-connection when DB is become available. I don't hope developers make some code to monitor DB's status, because I hope node-odata can support more DB type not only MongoDB. If developers should do this, it will become complex.

zackyang000 commented 8 years ago

Add event handle on v0.7.15.

Example of use:

server.on('connected', function() {
  console.log('MongoDB connected!');
});
server.on('disconnected', function() {
  console.log('MongoDB disconnected!');
});

on error is not necessary because we set the retry time to the maximum.

// Good way to make sure mongoose never stops trying to reconnect
mongoose.connect(uri, { server: { reconnectTries: Number.MAX_VALUE } });