How to stub mongoose methods with multiple arguments in Sinon?
To unit test functions chained like this simply chain stub
and spy
instances and verify that they were called with the expected values:
it('should find post by category id', function () { const limitSpy = sinon.spy(); const skipStub = sinon.stub().returns({ limit: limitSpy }); const sortStub = sinon.stub().returns({ skip: skipStub }); const findStub = sinon.stub(Post, 'find').returns({ sort: sortStub }); postDao.findPostsByCategoryId(1, 2, 3); sinon.assert.calledWithExactly(findStub, { 'categoryId': 1 }); // SUCCESS sinon.assert.calledWithExactly(sortStub, { 'createdAt': -1 }); // SUCCESS sinon.assert.calledWithExactly(skipStub, 2); // SUCCESS sinon.assert.calledWithExactly(limitSpy, 3); // SUCCESS});
Here is the unit test solution:
dao.js
:
const Post = require("./models/post");function findPostsByCategoryId(categoryId, first, second) { var sortingOrd = { createdAt: -1 }; return Post.find({ categoryId: categoryId }) .sort(sortingOrd) .skip(first) .limit(second);}module.exports = { findPostsByCategoryId,};
./models/post.js
:
// simulate Post modelconst Post = { find(where) { return this; }, sort(...args) { return this; }, skip(...args) { return this; }, limit(n) {},};module.exports = Post;
dao.test.js
:
const dao = require("./dao");const Post = require("./models/post");const sinon = require("sinon");const { expect } = require("chai");describe("Name of the group", () => { afterEach(() => { sinon.restore(); }); it("should pass", () => { sinon.stub(Post); Post.find.returnsThis(); Post.sort.returnsThis(); Post.skip.returnsThis(); const mResponse = { rowCount: 100 }; Post.limit.resolves(mResponse); return dao.findPostsByCategoryId(1, 2, 3).then((response) => { expect(response).to.be.eql(mResponse); sinon.assert.calledWithExactly(Post.find, { categoryId: 1 }); sinon.assert.calledWithExactly(Post.sort, { createdAt: -1 }); sinon.assert.calledWithExactly(Post.skip, 2); sinon.assert.calledWithExactly(Post.limit, 3); }); });});
Unit test result with coverage report:
54920719 ✓ should pass 1 passing (14ms)-----------------|----------|----------|----------|----------|-------------------|File | % Stmts | % Branch | % Funcs | % Lines | Uncovered Line #s |-----------------|----------|----------|----------|----------|-------------------|All files | 89.66 | 100 | 55.56 | 89.66 | | 54920719 | 100 | 100 | 100 | 100 | | dao.js | 100 | 100 | 100 | 100 | | dao.test.js | 100 | 100 | 100 | 100 | | 54920719/models | 40 | 100 | 0 | 40 | | post.js | 40 | 100 | 0 | 40 | 4,7,10 |-----------------|----------|----------|----------|----------|-------------------|
Source code: https://github.com/mrdulin/mocha-chai-sinon-codelab/tree/master/src/stackoverflow/54920719