Тестирование экспресс-промежуточного программного обеспечения

1

У меня есть следующий код для тестирования:

const Status = require('http-status-codes');
const passport = require('passport');
const Users = require('../models/users.js');

const authentication = {
    // Authenticate User Middleware
    authenticateUser: function authenticateUser(req, res, next) {
        return passport.authenticate('bearer', { session: false, failWithError: false },
            (err, user, info) => {
                if (err) {
                    return res.status(500).json({ message: err });
                }

                if (user) {
                    return Users.findOne({ auth_ref: user.auth_ref })
                        .populate('groups')
                        .exec((e, doc) => {
                            if (e) {
                                return res.status(500).json({ message: e });
                            }
                            req.authInfo = info;
                            req.user = doc;
                            return next(null, doc, info);
                        });
                }
                return res.status(Status.UNAUTHORIZED).json({ message: 'Access denied' });
            }
        )(req, res, next);
    },
};

module.exports = authentication.authenticateUser;

Мой тестовый файл:

const test = require('ava');
const sinon = require('sinon');
const proxyquire = require('proxyquire');

const Util = require('../util');

Util.beforeEach(test, (t) => {
    const authenticateStub = sinon.stub();
    const passportStub = {
        authenticate: authenticateStub,
    };
    const authenticationMocked = proxyquire('../../../middleware/authentication', { passport: passportStub });
    t.context.authenticateStub = authenticateStub;
    t.context.authenticationMocked = authenticationMocked;
});
Util.afterEach(test);
Util.after(test);

test('[middleware/authentication] authenticateUser function call succeed', sinon.test(async (t) => {
    // given
    const func = t.context.authenticationMocked;
    t.context.authenticateStub.withArgs(sinon.match.any, sinon.match.any, sinon.match.any).yields('error', { statusCode: 500 }, 'sampleUser');
    const nextSpy = sinon.spy();

    const fakeReq = { user: { email: '' } };
    const res = {
        status: () => res,
        json: () => res,
    };
    // when
    func(fakeReq, res, nextSpy);
    // then
})

Моя проблема в том, что я каким-то образом не могу издеваться над параметром res таким образом, чтобы не возникала ошибка. Этот код вызывает следующую ошибку:

  Rejected promise returned by test. Reason:

  TypeError {
    message: 'passport.authenticate(...) is not a function',   }

Если я удалю объект res с {} то ошибка будет res.status is not a function

Я что-то не так с инициализацией, или мой объект res не прав?

Теги:
unit-testing
sinon
ava

1 ответ

0
Лучший ответ

Теперь я нашел следующее решение:

// given
const func = t.context.authenticationMocked;
t.context.authenticateStub.withArgs(sinon.match.any, sinon.match.any, sinon.match.any).yields('error', { statusCode: 500 }, 'sampleUser').returns(() => {});
const nextSpy = sinon.spy();

const fakeReq = { user: { email: '' } };
const rootRouteStub = {
    status: sinon.stub(),
    json: sinon.spy(),
};
rootRouteStub.status.returns(rootRouteStub);
// when
func(fakeReq, rootRouteStub, nextSpy);

Ещё вопросы

Сообщество Overcoder
Наверх
Меню