抛出摩卡异常可以在不应该通过的时候通过测试
Throwing mocha exception can make a test pass when it should not
在我们的 mocha 测试中,有时我们会出现错误并抛出异常,当抛出这些异常时,不会调用后续的断言,即使出现问题,我们的测试也可能会通过。
// this would pass
it('adsf', async () => {
assert.equal(1,1)
var foo = undefined;
foo.hi(); // throw exception
assert.equal(1,2) // assert not called
});
我们尝试将其包装在 try catch 中,如下所示
// this would fail, but not say why
it('adsf', async () => {
try {
assert.equal(1,1)
// var foo = undefined;
// foo.hi();
assert.equal(1,2)
} catch (err) {
assert.fail(err) // if fail, such as the 1,2 case above, the line number of the error is not shown
}
});
但是 catch
案例隐藏了一些失败的断言信息。如果有人有任何建议,我们将不胜感激。
您示例中的测试不会通过。在 mocha 中,如果在测试中调用的函数抛出异常,则测试将失败。示例:
const assert = require('assert');
function foo() {
throw new Error('err');
}
describe('test', () => {
it('works', async () => {
foo();
console.log('came here');
});
});
$ npx mocha test.js
test
1) works
0 passing (6ms)
1 failing
1) test
works:
Error: err
at foo (test.js:8:9)
at Context.<anonymous> (test.js:13:11)
at processImmediate (internal/timers.js:439:21)
因此,在您的示例中,由于 foo.hi
抛出 TypeError
,它将被 mocha 捕获并显示为测试失败(执行确实不会达到断言,但测试将是无论如何都显示为失败)。
我怀疑在您的案例中发生的是做出承诺或拒绝承诺,例如以下示例之一:
function throwing() {
return new Promise((resolve, reject) => { throw new Error('err'); });
}
function rejecting() {
return new Promise((resolve, reject) => { reject(new Error('err')); });
}
describe('test', () => {
it('works', async () => {
throwing();
rejecting();
console.log('came here');
});
});
$ npx mocha test.js
test
came here
✓ works
[some UnhandledPromiseRejectionWarnings here]
1 passing (6ms)
两者都不会被测试捕获,因为函数成功执行并返回一个承诺并且测试块完成,但失败发生在稍后。如果您的函数 returns 是一个承诺,只需 await
在您的测试中对其进行测试以确保您获得承诺结果:
describe('test', () => {
it('works', async () => {
await throwing();
await rejecting();
console.log('came here');
});
});
$ npx mocha test.js
test
1) works
0 passing (6ms)
1 failing
1) test
works:
Error: err
at test.js:4:51
at new Promise (<anonymous>)
at throwing (test.js:4:10)
at Context.<anonymous> (test.js:13:11)
at processImmediate (internal/timers.js:439:21)
在我们的 mocha 测试中,有时我们会出现错误并抛出异常,当抛出这些异常时,不会调用后续的断言,即使出现问题,我们的测试也可能会通过。
// this would pass
it('adsf', async () => {
assert.equal(1,1)
var foo = undefined;
foo.hi(); // throw exception
assert.equal(1,2) // assert not called
});
我们尝试将其包装在 try catch 中,如下所示
// this would fail, but not say why
it('adsf', async () => {
try {
assert.equal(1,1)
// var foo = undefined;
// foo.hi();
assert.equal(1,2)
} catch (err) {
assert.fail(err) // if fail, such as the 1,2 case above, the line number of the error is not shown
}
});
但是 catch
案例隐藏了一些失败的断言信息。如果有人有任何建议,我们将不胜感激。
您示例中的测试不会通过。在 mocha 中,如果在测试中调用的函数抛出异常,则测试将失败。示例:
const assert = require('assert');
function foo() {
throw new Error('err');
}
describe('test', () => {
it('works', async () => {
foo();
console.log('came here');
});
});
$ npx mocha test.js
test
1) works
0 passing (6ms)
1 failing
1) test
works:
Error: err
at foo (test.js:8:9)
at Context.<anonymous> (test.js:13:11)
at processImmediate (internal/timers.js:439:21)
因此,在您的示例中,由于 foo.hi
抛出 TypeError
,它将被 mocha 捕获并显示为测试失败(执行确实不会达到断言,但测试将是无论如何都显示为失败)。
我怀疑在您的案例中发生的是做出承诺或拒绝承诺,例如以下示例之一:
function throwing() {
return new Promise((resolve, reject) => { throw new Error('err'); });
}
function rejecting() {
return new Promise((resolve, reject) => { reject(new Error('err')); });
}
describe('test', () => {
it('works', async () => {
throwing();
rejecting();
console.log('came here');
});
});
$ npx mocha test.js
test
came here
✓ works
[some UnhandledPromiseRejectionWarnings here]
1 passing (6ms)
两者都不会被测试捕获,因为函数成功执行并返回一个承诺并且测试块完成,但失败发生在稍后。如果您的函数 returns 是一个承诺,只需 await
在您的测试中对其进行测试以确保您获得承诺结果:
describe('test', () => {
it('works', async () => {
await throwing();
await rejecting();
console.log('came here');
});
});
$ npx mocha test.js
test
1) works
0 passing (6ms)
1 failing
1) test
works:
Error: err
at test.js:4:51
at new Promise (<anonymous>)
at throwing (test.js:4:10)
at Context.<anonymous> (test.js:13:11)
at processImmediate (internal/timers.js:439:21)