如何在nodejs中使用jest模拟核心节点模块的特定功能
how to mock a specific function of a core node module using jest in nodejs
我想模拟nodejs "crypto" 模块的特定方法。
我正在使用 jest 框架测试代码中的端点。
这是我的电子邮件验证端点代码的样子:
/* engnr_cntrlr.js */
exports.engineeremail_verifcation = async(req, res) => {
try {
// 3. i want to mock the next statement and return a mock-value to hashedToken variable
const hashedToken = crypto
.createHash('sha256')
.update(req.params.token)
.digest('hex');
const engnr = await Engineer.findOne({
engnrToken : hashedToken
}).orFail(new Error ('engnr not found'));
engnr.emailVerify = true
await engnr.save()
return res.status(202).send({ message: 'email verified' });
} catch (error) {
res.status(400).send({ error: error.message });
}
};
测试脚本:
/* tests/engineer.test.js */
test('engineer verifies his email', async done => {
// 1. i am fetching an engnr using an email id
engnr = await Engineer.findOne({
email: engineerOne.email
});
try {
const response = await request(app)
.put(`/api/engineer/confirm_mail/${engnr.token}`) //2. i am sending a hashed token as a req.params
.send();
expect(response.statusCode).toBe(202);
expect(response.body).toMatchObject({
message: 'email verified'
});
done();
} catch (error) {
done(error);
}
});
我面临的问题是在我的 'engineeremail_verification' 中模拟加密实现(就在第 3 条评论下方)。我在代码的其他部分使用了其他加密方法,我不想模拟它们。我只想模拟加密模块的这个特定实现,并返回一个模拟值。我怎么做?谢谢你回答我的问题。感谢任何形式的帮助。
您可以使用jest.spyOn(object, methodName)单独模拟crypto.createHash
。
例如
app.js
:
const crypto = require('crypto');
const express = require('express');
const app = express();
app.put('/api/engineer/confirm_mail/:token', async (req, res) => {
try {
const hashedToken = crypto.createHash('sha256').update(req.params.token).digest('hex');
console.log(hashedToken);
return res.status(202).send({ message: 'email verified' });
} catch (error) {
res.status(400).send({ error: error.message });
}
});
app.put('/example/:token', async (req, res) => {
const hashedToken = crypto.createHash('sha256').update(req.params.token).digest('hex');
console.log(hashedToken);
res.sendStatus(200);
});
module.exports = app;
app.test.js
:
const app = require('./app');
const request = require('supertest');
const crypto = require('crypto');
describe('61368162', () => {
it('should verify email', async () => {
const hashMock = {
update: jest.fn().mockReturnThis(),
digest: jest.fn().mockReturnValueOnce('encrypt 123'),
};
const createHashMock = jest.spyOn(crypto, 'createHash').mockImplementationOnce(() => hashMock);
const logSpy = jest.spyOn(console, 'log');
const engnr = { token: '123' };
const response = await request(app).put(`/api/engineer/confirm_mail/${engnr.token}`).send();
expect(createHashMock).toBeCalledWith('sha256');
expect(hashMock.update).toBeCalledWith('123');
expect(hashMock.digest).toBeCalledWith('hex');
expect(logSpy).toBeCalledWith('encrypt 123');
expect(response.statusCode).toBe(202);
expect(response.body).toMatchObject({ message: 'email verified' });
createHashMock.mockRestore();
logSpy.mockRestore();
});
it('should restore crypto methods', async () => {
const logSpy = jest.spyOn(console, 'log');
const response = await request(app).put('/example/123');
expect(jest.isMockFunction(crypto.createHash)).toBeFalsy();
expect(response.statusCode).toBe(200);
expect(logSpy).toBeCalledWith(expect.any(String));
logSpy.mockRestore();
});
});
集成测试结果与覆盖率报告:
PASS Whosebug/61368162/app.test.js (13.621s)
61368162
✓ should verify email (44ms)
✓ should restore crypto methods (5ms)
console.log node_modules/jest-environment-enzyme/node_modules/jest-mock/build/index.js:866
encrypt 123
console.log node_modules/jest-environment-enzyme/node_modules/jest-mock/build/index.js:866
a665a45920422f9d417e4867efdc4fb8a04a1f3fff1fa07e998e86f7f7a27ae3
----------|---------|----------|---------|---------|-------------------
File | % Stmts | % Branch | % Funcs | % Lines | Uncovered Line #s
----------|---------|----------|---------|---------|-------------------
All files | 93.75 | 100 | 100 | 92.86 |
app.js | 93.75 | 100 | 100 | 92.86 | 12
----------|---------|----------|---------|---------|-------------------
Test Suites: 1 passed, 1 total
Tests: 2 passed, 2 total
Snapshots: 0 total
Time: 15.707s
源代码:https://github.com/mrdulin/react-apollo-graphql-starter-kit/tree/master/Whosebug/61368162
我想模拟nodejs "crypto" 模块的特定方法。
我正在使用 jest 框架测试代码中的端点。
这是我的电子邮件验证端点代码的样子:
/* engnr_cntrlr.js */
exports.engineeremail_verifcation = async(req, res) => {
try {
// 3. i want to mock the next statement and return a mock-value to hashedToken variable
const hashedToken = crypto
.createHash('sha256')
.update(req.params.token)
.digest('hex');
const engnr = await Engineer.findOne({
engnrToken : hashedToken
}).orFail(new Error ('engnr not found'));
engnr.emailVerify = true
await engnr.save()
return res.status(202).send({ message: 'email verified' });
} catch (error) {
res.status(400).send({ error: error.message });
}
};
测试脚本:
/* tests/engineer.test.js */
test('engineer verifies his email', async done => {
// 1. i am fetching an engnr using an email id
engnr = await Engineer.findOne({
email: engineerOne.email
});
try {
const response = await request(app)
.put(`/api/engineer/confirm_mail/${engnr.token}`) //2. i am sending a hashed token as a req.params
.send();
expect(response.statusCode).toBe(202);
expect(response.body).toMatchObject({
message: 'email verified'
});
done();
} catch (error) {
done(error);
}
});
我面临的问题是在我的 'engineeremail_verification' 中模拟加密实现(就在第 3 条评论下方)。我在代码的其他部分使用了其他加密方法,我不想模拟它们。我只想模拟加密模块的这个特定实现,并返回一个模拟值。我怎么做?谢谢你回答我的问题。感谢任何形式的帮助。
您可以使用jest.spyOn(object, methodName)单独模拟crypto.createHash
。
例如
app.js
:
const crypto = require('crypto');
const express = require('express');
const app = express();
app.put('/api/engineer/confirm_mail/:token', async (req, res) => {
try {
const hashedToken = crypto.createHash('sha256').update(req.params.token).digest('hex');
console.log(hashedToken);
return res.status(202).send({ message: 'email verified' });
} catch (error) {
res.status(400).send({ error: error.message });
}
});
app.put('/example/:token', async (req, res) => {
const hashedToken = crypto.createHash('sha256').update(req.params.token).digest('hex');
console.log(hashedToken);
res.sendStatus(200);
});
module.exports = app;
app.test.js
:
const app = require('./app');
const request = require('supertest');
const crypto = require('crypto');
describe('61368162', () => {
it('should verify email', async () => {
const hashMock = {
update: jest.fn().mockReturnThis(),
digest: jest.fn().mockReturnValueOnce('encrypt 123'),
};
const createHashMock = jest.spyOn(crypto, 'createHash').mockImplementationOnce(() => hashMock);
const logSpy = jest.spyOn(console, 'log');
const engnr = { token: '123' };
const response = await request(app).put(`/api/engineer/confirm_mail/${engnr.token}`).send();
expect(createHashMock).toBeCalledWith('sha256');
expect(hashMock.update).toBeCalledWith('123');
expect(hashMock.digest).toBeCalledWith('hex');
expect(logSpy).toBeCalledWith('encrypt 123');
expect(response.statusCode).toBe(202);
expect(response.body).toMatchObject({ message: 'email verified' });
createHashMock.mockRestore();
logSpy.mockRestore();
});
it('should restore crypto methods', async () => {
const logSpy = jest.spyOn(console, 'log');
const response = await request(app).put('/example/123');
expect(jest.isMockFunction(crypto.createHash)).toBeFalsy();
expect(response.statusCode).toBe(200);
expect(logSpy).toBeCalledWith(expect.any(String));
logSpy.mockRestore();
});
});
集成测试结果与覆盖率报告:
PASS Whosebug/61368162/app.test.js (13.621s)
61368162
✓ should verify email (44ms)
✓ should restore crypto methods (5ms)
console.log node_modules/jest-environment-enzyme/node_modules/jest-mock/build/index.js:866
encrypt 123
console.log node_modules/jest-environment-enzyme/node_modules/jest-mock/build/index.js:866
a665a45920422f9d417e4867efdc4fb8a04a1f3fff1fa07e998e86f7f7a27ae3
----------|---------|----------|---------|---------|-------------------
File | % Stmts | % Branch | % Funcs | % Lines | Uncovered Line #s
----------|---------|----------|---------|---------|-------------------
All files | 93.75 | 100 | 100 | 92.86 |
app.js | 93.75 | 100 | 100 | 92.86 | 12
----------|---------|----------|---------|---------|-------------------
Test Suites: 1 passed, 1 total
Tests: 2 passed, 2 total
Snapshots: 0 total
Time: 15.707s
源代码:https://github.com/mrdulin/react-apollo-graphql-starter-kit/tree/master/Whosebug/61368162