On May 30, 2019, at 11:01 PM, Ryosuke Niwa <rniwa@webkit.org> wrote:

I’m gonna give you a game changing function:

function listenForEventOnce(target, name, timeout) {
    return new Promise((resolve, reject) => {
        const timer = timeout ? setTimeout(reject, timeout) : null;
        target.addEventListener(name, () => {
            if (timer)
                clearTimeout(timer);
            resolve();
        }, {once: true});
    });
}

You can then write a test like this:
await listenForEventOnce(document.body, 'load');
// do stuff after load event.

await listenForEventOnce(document.querySelector('input'), 'focus');
await listenForEventOnce(visualViewport, 'scroll', 5000);
// After the input element is focused, then the visual viewport scrolled or 5 seconds has passed.

Ryosuke++.

Just FYI, if you’re writing LayoutTests, we’ve got something very similar in LayoutTests/media/video-test.js:

function waitFor(element, type) {
    return new Promise(resolve => {
        element.addEventListener(type, event => {
            consoleWrite(`EVENT(${event.type})`);
            resolve(event);
        }, { once: true });
    });
}

And:

function sleepFor(duration) {
    return new Promise(resolve => {
        setTimeout(resolve, duration);
    });
}

And also:

function shouldReject(promise) {
    return new Promise((resolve, reject) => {
        promise.then(result => {
            logResult(Failed, 'Promise resolved incorrectly');
            reject(result);
        }).catch((error) => {
            logResult(Success, 'Promise rejected correctly');
            resolve(error);
        });
    });
}

So you could also do:

await Promise.race(waitFor(document.body, ‘load’), shouldReject(sleepFor(5000)));

Although we’d probably want a new function, “rejectIn(duration)”, and then it’d be:

await shouldResolve(Promise.race(waitFor(document.body, ‘load’), rejectIn(5000)));

But all that said, I agree that wrapping events in Promises makes it very easy to write readable, single `async` function test cases. A+++, would write test again.

-Jer


- R. Niwa

_______________________________________________
webkit-dev mailing list
webkit-dev@lists.webkit.org
https://lists.webkit.org/mailman/listinfo/webkit-dev