How to tell if an async funcion has been invoked w

2019-03-01 16:00发布

async function sleep(msecs){

    if (!somebodyAwaitsMe())            // that's the unknown
        throw ("call me with await");

    return new Promise(resolve => setTimeout(resolve, ms));
}

await sleep(5000);                    // correct

sleep(5000);                     // forgot await, returns immediately,

I want to know, inside an async function, if it has been called with await or not, is that possible?

The code exemplifies a possible situation to help detect mistakes but it may be useful in other situations where a function may be invoked by design, with or without await.

1条回答
戒情不戒烟
2楼-- · 2019-03-01 16:37

No, this is not possible (without a debugger). And it's not the responsibility of your function anyway to check what its caller does. You should just always return your promise.

While you cannot inspect and verify the code of your caller (or its caller or …) if for security reasons alone, or also because static analysis is hard, you still can dynamically observe whether your promise is awaited. All you need to do is emit a warning when the .then() method isn't called immediately:

function expectMethodInvocation(o, p) {
    const t = setTimeout(() => {
        console.warn("You should call my "+p+" method!");
        delete o[p];
    }, 0);
    o[p] = function(...args) {
        clearTimeout(t);
        delete o[p];
        return o[p].call(this, ...args);
    };
    return o;
}

function sleep(ms) {
    const p = new Promise(resolve => setTimeout(resolve, ms));
    return expectMethodInvocation(p, "then");
}

(async function() {
    await sleep(1000);
    console.log("OK");
    sleep(1000); 
    console.log("Ooops");
})();
查看更多
登录 后发表回答