I'm developing a restApi using Hapi js. The structure of the project is like the following:
|-Root
server.js
|-router
routes.js
|-handlers
authHandler.js
|-db
userDb.js
An authentication request would hit the routes.js and forwarded to authHandler.js which in turn calls userDb.js. userDb.js talk to a database and returns the result to authHandler.js which return the response to the client.
I've been trying write a test where the userDb.js doesn't talk to the database
For this i'm using Hapi's inject to be able to call the routes without actually starting the server. I'm struggling to figure out how to mock the database in the call chain so that I can supply a dummy response.
So in short, I want the userDb.js to be replaced by a mock when testing.
After the suggestion from @AlbertZaccagni above, I consulted the documentation of sinon and I came up with the following:
NB: I have omittet some code that declares the routes and other non essential parts to the question at hand.
Assuming that userDb.js is the module that connects to the database, and that I want to mock the response from the database:
userDb.js looks like this:
var db = require(/*path to db */);
module.exports.getUser = function(id, callback){
db.query('sql query', function(err, rows){
if(err){
return callback(err);
}
return callback(null, rows[0]);/*returns the first object-
in the resultset from the database.*/
});
}
Inside my test folder I created a file called mytest.js with the following content:
//don't forget to install sinon JS via npm
var sinon = require('sinon');
var server = require(/*path to hapi server*/);
var userDb = require(/*path to the module we are stubbing/mocking*/);
describe('Stub test', function(){
var options = {};
options.method = 'GET';
options.url = '/user/1';
it('with stubbing', function(done) {
var stub = sinon.stub(userDb, 'getUser', function(id, callback) {
if (id < 5) {
return callback(null, 100);/*in this case i'm just testing
to see if this function
will get called instead-
of the actual function. That's why 100.*/
}
return new Error('test error');
});
server.inject(options, function(res) {
var result = res.result;
res.statusCode.should.equal(200);
result.num.should.equal(100);
done();
});
});
});
When I run npm test on my working directory, I see that It passes without actually calling the database and it returns 100 for the username 1.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With