过去两周来,我一直在写测试。在我的工作场所,我们使用Mocha作为测试运行程序,并使用Chai作为声明库。我还使用Sinon来创建存根,并且有一些东西经常困扰着我。我已经为几个函数编写了测试,在其中测试了函数中的每个依赖关系,最糟糕的是,我什至没有考虑要测试的函数接受的参数。让我举个例子
module.exports = {
"someFunc": (arg1, arg2) => {
return new Promise((resolve, reject) => {
Promise.all(arg1).then(data => {
let someArray = ourHelperLib.toArray(data);
let someObj = ourHelperLib.toObject(arg2);
if(someArray.length == 0){
reject("error");
}else{
resolve({
"array": someArray,
"object": someObj
});
}
}).catch(err => {
reject(err);
});
});
},
}
Promise.all()
引发错误的情况。Promise.all()
存根返回一个假正值,而将ourHelperLib.toArray()
存根以引发错误并检查函数是否处理错误。Promise.all()
,ourHelperLib.toArray()
和ourHelperLib.toObject()
进行了存根处理,以返回误报,然后检查输出中是否有已解决的承诺,其值是操作的结果。 从函数定义中可以很明显地看出,传递给函数的两个参数都直接传递给我正在存根的依赖项,因此我可以完全忽略那些值,这就是我的意思
const stubOurHelperLibToThrowError = argFromCaller => {
throw new Error("This is an error");
}
由于我不处理传递给存根函数的参数,因此我根本不会根据传递给存根函数的数据来测试该函数。我只是在测试函数someFunc()
的逻辑结构。
这是一个好习惯吗?我还没有找到很多可靠的答案,而且由于我负责介绍编写当前正在工作的单元测试的指南,所以我认为这很关键。
和平!
答案 0 :(得分:1)
您可以将promise传递给您的函数,而不必为您正在描述的内容添加任何内容。
在某些情况下,我对Promise.all()存根以引发错误
与其对存根Promise.all
进行存根而不是存根,只需将具有拒绝的Promise
的数组传递给函数:
someFunc([Promise.reject(new Error('fail'))], null)
...这将导致Promise.all
落入catch
并因错误而拒绝。
我将Promise.all()存根以返回一个假正值,然后将ourHelperLib.toArray()存根以引发错误并检查函数是否处理
再次,而不是对Promise.all
进行存根处理,只需传递具有解析的Promise
的数组:
someFunc([Promise.resolve('a value')], null)
您可以存根ourHelperLib.toArray
引发错误,也可以让Promise
数组解析为已知会导致ourHelperLib.toArray
引发的错误。
对于我的第三个测试,我对Promise.all(),ourHelperLib.toArray()和ourHelperLib.toObject()进行存根以返回假阳性结果,然后检查输出中是否有已解决的承诺,其值是操作的结果。
对ourHelperLib.toArray
和ourHelperLib.toObject
进行插拔是可选的。除非它们在计算上很昂贵(例如,如果进行网络调用),那么通常都可以像平常一样调用它们。
您可以在解析的ourHelperLib.toArray
数组中传递要给Promise
的数据,只需将要发送的值作为第二个参数传递给ourHelperLib.toObject
:< / p>
someFunc([
Promise.resolve('value 1 for ourHelperLib.toArray'),
Promise.resolve('value 2 for ourHelperLib.toArray')
], 'value for ourHelperLib.toObject')
...并检查结果Promise
是否解析为期望值。
通常,最佳做法是坚持黑盒测试。
此函数似乎没有任何副作用,仅返回一个Promise
即可根据传递的参数将其解析为结果。
除非该函数具有计算上昂贵的依赖关系,否则只要有可能,最好通过简单地传递参数并验证结果来测试此类函数。