Node.js 已调用未注册的Sinon Spy(异步/等待)
当我运行测试“Should call getDetails()”时,它失败了,并显示一条消息,说明该函数被调用了0次。如果我记录间谍,我可以看到它的道具“called”等于false。我知道正在调用它,因为我在Node.js 已调用未注册的Sinon Spy(异步/等待),node.js,express,mocha.js,sinon,Node.js,Express,Mocha.js,Sinon,当我运行测试“Should call getDetails()”时,它失败了,并显示一条消息,说明该函数被调用了0次。如果我记录间谍,我可以看到它的道具“called”等于false。我知道正在调用它,因为我在getDetails中有一个控制台。log,每次调用getMultipleRecords()时它都会显示出来。第一个测试工作正常,但是findAll()是一个承诺,所以我知道这是一个异步问题 我认为问题在于摩卡不尊重等待的。任何人的反馈都将不胜感激 测试: description('get
getDetails
中有一个控制台。log
,每次调用getMultipleRecords()
时它都会显示出来。第一个测试工作正常,但是findAll()
是一个承诺,所以我知道这是一个异步问题
我认为问题在于摩卡不尊重等待的。任何人的反馈都将不胜感激
测试:
description('getMultipleRecords()',()=>{
让next=()=>{};
let req={body:{records:[1,2,3]};
设res={};
//通过
它('应该调用VMBilling.findAll()',异步函数(){
var findAll=sinon.spy(VMBilling,'findAll');
等待记录Ctrl.getMultipleRecords(请求、恢复、下一步);
//console.log(查找)
sinon.assert.calledOnce(findAll);
});
//失败的
它('应该调用getDetails()',异步函数(){
var gd=sinon.spy(recordCtrl,'getDetails');
等待记录Ctrl.getMultipleRecords(请求、恢复、下一步);
sinon.assert.calledOnce(gd);
});
});
我正在测试的函数
const getMultipleRecords = async (req, res, next) => {
try {
console.log('getMultipleRecords()');
let records = await VMBilling.findAll({
include: [
{
model: ErrorMessage,
},
],
where: [
{
id: req.body.records,
},
],
});
let recordsWithDetails = getDetails(records);
console.log(recordsWithDetails);
return res.status(200).json(recordsWithDetails);
} catch (error) {
next(error);
}
}
因为编译后,函数以不同的签名导出,使用全名,在存根时,我们存根全局函数,但在从另一个函数中调用它时,我们调用本地函数,因此它不起作用。有一个解决方法可以做到这一点
以下是单元测试解决方案:
controller.ts
从“/model”导入{VMBilling};
const getDetails=记录=>{
控制台日志(记录);
};
const getMultipleRecords=async(请求、恢复、下一步)=>{
试一试{
log('getMultipleRecords()');
let records=wait VMBilling.findAll({
包括:[
{
型号:“ErrorMessage”
}
],
其中:[
{
id:req.body.records
}
]
});
let recordsWithDetails=exports.getDetails(记录);
控制台日志(记录详细信息);
返回res.status(200).json(recordsWithDetails);
}捕获(错误){
下一步(错误);
}
};
exports.getMultipleRecords=getMultipleRecords;
exports.getDetails=getDetails;
model.ts
:
export const VMBilling={
芬德尔(条件){
console.log(“条件”);
}
};
控制器规范ts
:
从“/model”导入{VMBilling};
从“sinon”进口sinon;
const recordCtrl=require('./控制器');
描述('getMultipleRecords()',()=>{
让next=()=>{};
let req={body:{records:[1,2,3]};
设res={};
之后(()=>{
sinon.restore();
});
它('应该调用VMBilling.findAll()',异步函数(){
var findAll=sinon.spy(VMBilling,'findAll');
等待记录Ctrl.getMultipleRecords(请求、恢复、下一步);
sinon.assert.calledOnce(findAll);
});
它('应该调用getDetails()',异步函数(){
var gd=sinon.spy(recordCtrl,'getDetails');
等待记录Ctrl.getMultipleRecords(请求、恢复、下一步);
sinon.assert.calledOnce(gd);
});
});
100%覆盖率的单元测试结果:
getMultipleRecords()
getMultipleRecords()
条件
未定义
未定义
✓ 应该调用VMBilling.findAll()
getMultipleRecords()
条件
未定义
未定义
✓ 应该调用getDetails()
2次通过(9ms)
--------------------|----------|----------|----------|----------|-------------------|
文件|%Stmts |%Branch |%Funcs |%Line |未覆盖行|s|
--------------------|----------|----------|----------|----------|-------------------|
所有文件| 100 | 100 | 100 | 100 ||
控制器规范ts | 100 | 100 | 100 | 100 ||
controller.ts | 100 | 100 | 100 | 100 ||
型号:ts | 100 | 100 | 100 | 100 ||
--------------------|----------|----------|----------|----------|-------------------|
源代码:谢谢,这解决了我的问题。我发现的主要区别是您将getDetails()更改为exports.getDetails()。为什么需要指定模块?导入时,我实际上是在创建一个新实例,因此在测试中,我指的是getDetails()的另一个实例?@austinb91 Update answer,请检查。