为什么等待等待我的自定义承诺的请求挂起?

时间:2019-04-02 08:48:45

标签: javascript node.js express async-await mocha

我正在尝试使用Mocha在Express / Node后端中测试功能。我创建了一个实际参数的存根,该存根由函数修改:它有一个send方法,该方法在getValue(我要测试的函数)中调用,还有一个ready参数,我将其初始化为创建存根时的新承诺,并在存根上调用send时解决。

我正在尝试await,但是它只是挂了(然后Mocha超时了测试)。下面的setTimeout打印Promise { 'abc' },我认为这意味着诺言已经按照我的预期解决了,但是等待从未完成。

这是测试文件中的相关代码:

function ResStubTemplate() {
        return {
                _json: undefined,
                _message: undefined,
                json: function(x) {
                        this._json = x;
                        return this;
                },
                send: function(message) {
                        this._message = message;
                        this.ready = Promise.resolve("abc");
                        return this;
                },
                ready: new Promise(_ => {})
        }
}

// This is the test
it("should get the value.", async function(done) {
        let req = { query: { groupId: 12345 } };
        res = ResStubTemplate();
        controller.getValue(req, res);
        setTimeout(() => console.log(res.ready), 1000); // prints Promise { 'abc' }
        let x = await res.ready; // hangs??
        console.log(x); // never prints
        done();
}

这是测试文件中的相关代码:

exports.getValue = function(req, res) {
        ValueModel.findOne({groupId: req.query.groupId})
           .then(value => res.json({value: value}).send();                                                                                                         
};                                                                                                    

我得到的错误是:

Error: Timeout of 5000ms exceeded. 
For async tests and hooks, ensure "done()" is called; if returning a Promise,
ensure it resolves. (/.../test/api/controller_test.js)

1 个答案:

答案 0 :(得分:3)

当表达式:

let x = await res.ready; // hangs??

…被评估,其值为该代码创建的承诺:

ready: new Promise(_ => {})

从不兑现承诺,因此它一直在等待。

稍后您这样做:

 this.ready = Promise.resolve("abc");

…用一个新的(已解决的)承诺替换了该承诺,但是 new 承诺不是您正在等待的值。