In JS there are several ways of defining and instantiating a class. A really good article commenting ways of doing that, courtesy of jjeronimo, available here.
Based on the article mentioned above, and my previous experience with factories implementations in Java (an example), I propose to implement classes this way (lib/dao/user.js):
var sqlite3 = require('sqlite3').verbose();
var db = new sqlite3.Database('./db/db.sqlite');
this.newInstance = function() {
return new impl();
};
function impl() {
// ...
this.getUserById = function(id, callback) {
db.all("SELECT rowid AS id, name FROM user WHERE id=?", [ id ], function(err, rows) {
if (err)
console.log(err);
callback((rows)?rows[0]:null);
});
};
// ...
};
If you want to use the class defined above, you just have to do something like (lib/service/user.js):
var userDao = require('../dao/user');
// ...
this.getUserById = function(id, callback) {
userDao.newInstance().getUserById(id, callback);
};
// ...
One of the main advantages of this approach, factories based, is that you can mockup very easy your classes for testing. For example:
this.newInstance = function(env) {
if (env && env == 'test')
return new mock();
else
return new impl();
};
function impl() {
// Normal implementation
}
function mock() {
// Mockup implementation (for testing)
}
Then, if you want to test, you just have to specify the parameter test when instantiating the object, something like:
var service = require('service');
var serviceMock = service.newInstance('test');
// Test ...
var serviceReal = service.newInstance();
// Do something 'real'
No comments:
Post a Comment