skjindal93
skjindal93

Reputation: 734

Capture HAR from BrowserStack using webdriverio and browsermob

I am trying to use BrowserMob proxy to capture HAR for tests running on BrowserStack using WebdriverIO

I have the following code so far

conf/local.conf.js

const browserstack = require('browserstack-local');
const Proxy = require('browsermob-proxy').Proxy;
const fs = require('fs');

exports.config = {
    user: process.env.BROWSERSTACK_USERNAME || 'shubhamjindal2',
    key: process.env.BROWSERSTACK_ACCESS_KEY || 'PyNWYKCcnwxt4XMCP52s',
    proxyHost: process.env.PROXY_HOST || 'localhost',
    proxyPort: process.env.PROXY_PORT || '9090',

    updateJob: false,
    specs: [
        './test/specs/localTest.js'
    ],
    exclude: [],

    capabilities: [{
        'os': 'Windows',
        'os_version': '10',
        'browserName': 'Chrome',
        'browserVersion': '62.0',
        'browserstack.local': 'true',
        'browserstack.video': 'false',
        'seleniumProtocol': 'WebDriver'
    }],
    logLevel: 'warn',
    coloredLogs: true,
    screenshotPath: './errorShots/',
    baseUrl: '',
    waitforTimeout: 10000,
    connectionRetryTimeout: 90000,
    connectionRetryCount: 3,
    host: 'hub.browserstack.com',

    before: function() {
        const chai = require('chai');
        global.expect = chai.expect;
        chai.Should();
    },
    framework: 'mocha',
    mochaOpts: {
        ui: 'bdd',
        timeout: 60000
    },

    // Code to start browserstack local before start of test
    onPrepare: function(config, capabilities) {
        console.log("Connecting local");
        exports.proxy = new Proxy();

        exports.proxy.start(exports.config.proxyPort, function(err, data) {
            if (!err) {
                exports.proxy.startHAR(exports.config.proxyPort, 'dummy', true, true);
            } else {
                console.error(err);
            }
        });

        capabilities['proxy'] = {
            httpProxy: exports.proxy,
        };

        const bsLocalArgs = {
            'key': exports.config.key,
            'forcelocal': true,
            'forceproxy': true,
            'force': true,
            'v': true,
            '-local-proxy-host': exports.config.proxyHost,
            '-local-proxy-port': exports.config.proxyPort,
        };

        return new Promise(function(resolve, reject) {
            exports.bsLocal = new browserstack.Local();
            exports.bsLocal.start(bsLocalArgs, function(error) {
                if (error) return reject(error);

                console.log('Connected. Now testing...');
                resolve();
            });
        });
    },

    // Code to stop browserstack local after end of test
    onComplete: function(exitCode, config, capabilities, results) {
        exports.bsLocal.stop();

        exports.proxy.getHAR(exports.config.proxyPort, function(err, resp) {
            console.log(err, resp);
            if (!err) {
                console.log('har saved at output.har');
                fs.writeFileSync('test/diagnostics/output.har', resp, 'utf8');
            } else {
                console.err('Error getting HAR file: ' + err);
            }
            exports.proxy.stop(exports.config.proxyPort);
        });
    },
}

tests/spec/localTest.js

describe('BrowserStack Local Testing', function() {
    it('can check tunnel working', function() {
        browser.url('http://localhost:8083');
    });
});

I am stuck at getting HAR from proxy in onComplete hook, but I am unable to think of a way to get HAR.

Is this the right configuration? How do I end the browser with a callback, so that proxy is able to capture the HAR?

I am running the test using wdio cli

./node_modules/.bin/wdio conf/local.conf.js

Upvotes: 0

Views: 1716

Answers (2)

Haxor
Haxor

Reputation: 2306

If I understand correctly, you need to collect HAR for some reasons for the sessions running on BrowserStack. If so, then BrowserStack provides this feature of Network Logs, which you can get as a HAR file and contains all the network information which you will get from browser-mob. You can get the network logs by using their API.

Retrieving Automate network logs

Network Logs for each session are available to you in HAR (HTTP Archive) format, and these can be retrieved using REST API.

curl -u "USERNAME:ACCESS_KEY" https://api.browserstack.com/automate/builds/<build-id>/sessions/<session-id>/networklogs

and FYI, please redact your BrowserStack username and access key from the code you posted.

Upvotes: 1

ANM1996
ANM1996

Reputation: 161

I understand that you are using Webdriver IO to execute the tests. You can refer to the sample project by BrowserStack: https://github.com/browserstack/webdriverio-browserstack

Make changes in the local.conf.js file as follows by replacing the onPrepare function with the one shared below.

I am using Charles Proxy to capture the Network Traffic and it is working for me. Make sure to follow the steps as mentioned in the Readme.md file.

onPrepare: function (config, capabilities) {
    console.log("Connecting local");
    return new Promise(function(resolve, reject){
      exports.bs_local = new browserstack.Local();
      exports.bs_local.start({'key': exports.config.key,'forcelocal': true, 'verbose': 'true','force':'true','proxyHost': '127.0.0.1', 'proxyPort': '8888','forceProxy': true }, function(error) {
        if (error) return reject(error);
        console.log('Connected. Now testing...');

        resolve();
      });
    });
  },

Upvotes: 0

Related Questions