Search code examples
javascriptinternleadfoot

How to take screenshots inside execute or executeAsync using Intern


In this test I'm working on, I'm using executeAsync() to catch some events of the page being tested. I don't know the number of events that are going to happen and for each one that it's catched I want to take a screenshot with .takeScreenshot(). Currently, I'm using this code:

return this.parent
    .setExecuteAsyncTimeout(5000)
    .executeAsync(function(done) {
        window.events = function(event){
            if(event.message == 'takeScreenshot'){
                return done(event);
            } else if(event.message == 'endTest'){
                return done(event);
            }
        };
    }, [])
    .then(function(event){
         return this.parent
             .takeScreenshot()
             .then(function(data) {
                 //previously defined array to save the screenshots
                 bufferArray.push(data);
             })
    .end();
})

This code is working but the problem is that it only takes one screenshot since it only catches the first event and then finishes the test instead of waiting for the other events. Can anyone tell me if it's possible to call the .takeScreenshot() inside the .executeAsync() instead of returning the callback done(event)?


Solution

  • The takeScreenshot method can't be called from within executeAsync, so you'll need to do something else. Without async/await, recursion is probably the most straightforward solution, something like this (untested):

    function takeScreenshots() {
        return this.parent
            // Wait for a takeScreenshot or endTest event
            .executeAsync(function (done) {
                window.events = function (event) {
                    if (
                        event.message === 'takeScreenshot' ||
                        event.message === 'endTest'
                    ) {
                        done(event);
                    }
                };
            })
            .then(function (event) {
                // If the event was a takeScreenshot, take it and then
                // call takeScreenshots again to wait for another
                // event.
                if (event.message === 'takeScreenshot') {
                    return this.parent
                        .takeScreenshot()
                        .then(function (data) {
                            bufferArray.push(data);
                        })
                        .then(takeScreenshots);
                }
            });
    }
    
    return this.parent
        .setExecuteAsyncTimeout(5000)
        .then(takeScreenshots);