通过测试时可能未处理错误

时间:2015-02-16 08:44:12

标签: javascript promise mocha sinon bluebird

我有以下方法:

EventHandler.prototype.handle = function (event) {

    var me = this;
    return me.processEvent(event).then(function () {
        return me.saveLastSeenEventRevision(event);
    }).catch(function (err) {

        me.logger.debug("First attempt of event process failed, trying recovery");

        return me.recoveryStrategy.execute(event,me.processEvent.bind(me)).then(function()     {
            return me.saveLastSeenEventRevision(event);
        });
    });
};

我写了这个测试:

describe('when processEvent fails', function() {

    beforeEach(function () {
        instance.processEvent.returns(Bluebird.reject(new Error('rejection')));
    });

    describe('when recovery fails', function() {
        beforeEach(function () {
            instance.recoveryStrategy.execute.returns(Bluebird.reject(new Error('recovery rejected')));
        });

        it('should not save the revision', function(done) {
            instance.handle(event).catch(function() {
                sinon.assert.notCalled(instance.saveLastSeenEventRevision);
                done();
            }).done();
        });
    });
});

我模拟了对 processEvent 方法的拒绝,并且在捕获函数时我模拟了我的恢复实现的最终拒绝。我为此方法编写了更多测试,但设置是相同的。所有测试都按预期进行,但在控制台中我看到了这条消息:

Possibly unhandled Error: rejection

还有其他办法处理这些承诺通过这项测试吗?

测试设置 - mocha / chai / sinon,因为promise库使用bluebird。

2 个答案:

答案 0 :(得分:4)

嗯,你正在创建一个明确的拒绝但是没有在这里处理它:

instance.processEvent.returns(Bluebird.reject(new Error('rejection')));

蓝鸟看到你在这里创造了一个未处理的拒绝,所以它让你知道。这是因为真正的函数会在调用时返回拒绝,但是sinon会提前创建它 - 因此应用程序有一个未处理的未决错误位置。你可以用以下方式关闭它:

Bluebird.onPossiblyUnhandledRejection(function(){});

或者更好的是,使用像sinon-as-promised这样的工具,您可以这样做:

instance.processEvent.rejects('rejection');

另一方面 - 不要使用愚蠢的done语法,Mocha已经内置了promises支持。您可以通过测试return承诺。

答案 1 :(得分:1)

所以,问题在于sinon存根和设置返回值。看来,传递被拒绝的承诺作为返回值是在sinon内部进行评估的一些方法。

有两种选择:

  1. 不直接设置返回值,而是实现将用于代替存根的函数

    sinon.stub(instance, 'processEvent', function() {
        return Bluebird.reject(new Error('rejected');
    });
    
  2. 使用 sinon-as-promised 库,允许以下内容:

    sinon.stub(instance, 'processEvent').rejects(new Error('rejected'));