使用sinon和chai测试功能时的问题

时间:2018-09-20 04:47:48

标签: node.js sinon sinon-chai

我正在尝试开始在项目中使用测试,有些事情我能够正确测试,而另一些则不能。这是我要测试的功能。

exports.rateReview = async (req, res, next) => {
    try {
        const review = await Review.findById(req.body.id);
        if (review) {
            if (req.body.type === 'like') await review.like();

            if (req.body.type === 'dislike') await review.dislike();
        }

        res.send('Ok');
    } catch (err) {
        console.log(err);
    }
}

我要测试的是,是否根据req.body.type调用了like()和dislike()函数。所以这是我的测试文件。

const sinon = require('sinon');
const chai = require('chai');
const sinonChai = require("sinon-chai");
const mongoose = require('mongoose');

const seriesController = require('../../../../src/series-search/controllers/series.controller');
const Review = require('../../../../src/series-search/models/Review');

const expect = chai.expect;
chai.use(sinonChai);

let spyFindById, spyLike, spyDislike;

beforeEach(() => {
    spyLike = sinon.spy(Review.prototype, 'like');
    spyDislike = sinon.spy(Review.prototype, 'dislike');
    spyFindById = sinon.stub(Review, 'findById').returns({});
});

afterEach(() => {
    spyLike.restore();
    spyDislike.restore();
    spyFindById.restore();
});

describe('Series controller', () => {
    describe('search()', () => {

    });

    describe('addReview()', () => {
        it('should call findById() with review id');
    });

    describe('rateReview()', () => {
        it('should call review.like() if type is like', (done) => {
            const req = {
                body: {
                    id: '123456',
                    type: 'like'
                }
            };
            const res = {
                send: sinon.stub()
            };
            
            const spyLike = sinon.spy(review, 'like');
            seriesController.rateReview(req, res, null);

            expect(spyLike).to.have.been.calledOnce;
            done();
        });

        it('should call review.dislike() if type is dislike');
    });
});

测试一直失败,因为它说期望'like'被调用一次,但没有被调用。我尝试了很多事情,并在Google上进行了很多搜索,但无法正常工作。如果有人有任何想法,我将不胜感激。

谢谢!

1 个答案:

答案 0 :(得分:0)

正确的方法是在存根like方法时返回dislikefindById

....

let spyFindById, spyLike, spyDislike;

beforeEach(() => {
  spyLike = sinon.spy();
  spyDislike = sinon.spy();

  // spy `like` and `dislike` here so our `review` variable can be spied. 
  // use `resolves` since it is promised based function
  spyFindById = sinon.stub(Review, 'findById').resolves({
    like: spyLike,
    dislike: spyDislike
  });
});

afterEach(() => {
  sinon.restore(); // use sinon.restore() is enough if you use the latest Sinon
});

describe('Series controller', () => {
  describe('rateReview()', () => {

    // no need to use `done` if we can use `async await`
    it('should call review.like() if type is like', async () => {
      const req = {
        body: {
          id: '123456',
          type: 'like'
        }
      };
      const res = {
        send: sinon.stub()
      };

      await seriesController.rateReview(req, res, null);

      expect(spyLike).to.have.been.calledOnce;
    });

    it('should call review.dislike() if type is dislike');
  });
});