102

我希望能在这个问题上找到一些帮助。我正在尝试为我正在编写的应用程序编写测试。我已将问题提炼为以下示例代码。我想测试是否引发了错误。我使用 Testacular 作为测试运行程序,以 mocha 作为框架,chai 作为断言库。测试运行,但测试失败,因为抛出了错误!任何帮助是极大的赞赏!

function iThrowError() {
    throw new Error("Error thrown");
}

var assert = chai.assert,
    expect = chai.expect;
describe('The app', function() {
    describe('this feature', function() {
        it("is a function", function(){
            assert.throw(iThrowError(), Error, "Error thrown");
        });
    });
});
4

3 回答 3

149

你没有以assert.throws()正确的方式传递你的功能。

assert.throws()函数需要一个函数作为其第一个参数。在您的代码中,您正在调用 iThrowError 并在调用assert.throws().

基本上,改变这个:

assert.throws(iThrowError(), Error, "Error thrown");

对此:

assert.throws(iThrowError, Error, "Error thrown");

应该可以解决您的问题。

带参数:

assert.throws(() => { iThrowError(args) }, Error);

或者

assert.throws(function() { iThrowError(args) }, Error, /Error thrown/);
于 2013-07-22T17:14:04.170 回答
40

添加到最上面的答案,如果你需要调用你的函数作为测试的一部分(即你的函数应该只在传递某些参数时抛出错误),你可以将你的函数调用包装在一个匿名函数中,或者,在 ES6+ 中,您可以在箭头函数表达式中传递您的函数。

// Function invoked with parameter.
// TEST FAILS. DO NOT USE.
assert.throws(iThrowError(badParam), Error, "Error thrown"); // WRONG!

// Function invoked with parameter; wrapped in anonymous function for test.
// TEST PASSES.
assert.throws(function () { iThrowError(badParam) }, Error, "Error thrown");

// Function invoked with parameter, passed as predicate of ES6 arrow function.
// TEST PASSES.
assert.throws(() => iThrowError(badParam), Error, "Error thrown");

而且,为了彻底起见,这里有一个更字面的版本:

// Explicit throw statement as parameter. (This isn't even valid JavaScript.)
// TEST SUITE WILL FAIL TO LOAD. DO NOT USE, EVER.
assert.throws(throw new Error("Error thrown"), Error, "Error thrown"); // VERY WRONG!

// Explicit throw statement wrapped in anonymous function.
// TEST PASSES.
assert.throws(function () { throw new Error("Error thrown") }, Error, "Error thrown");

// ES6 function. (You still need the brackets around the throw statement.)
// TEST PASSES.
assert.throws(() => { throw new Error("Error thrown") }, Error, "Error thrown");
于 2016-11-07T20:06:44.663 回答
26

我看到您能够解决您的问题,但无法检查特定错误。要使用 Chai 的 expect/should 语法这样做,您可以使用来自throw()不同签名的参数:

@param{ ErrorConstructor } constructor
@param{ String | RegExp } expectederror message
@param{ String } message _optional_

在您的示例中,您应该能够使用以下任一项:

expect(iThrowError).to.throw(/Error thrown/);
expect(iThrowError).to.throw(Error, /Error thrown/);
expect(iThrowError).to.throw(new Error('Error thrown'));

而且(同样,来自 chai 的文档),您可以使用以下方法过滤其他错误消息:

expect(iThrowError).to.throw(Error).and.not.throw(/Another Error thrown/);

希望这可以帮助!

于 2013-02-21T18:53:49.530 回答