Local Testing with App Automate

Local Testing is a BrowserStack feature that helps you test mobile apps that access resources hosted in development or testing environments during automated test execution. This page will guide you through enabling Local Testing for App Automate sessions, and then using it to test apps that retrieve data from servers on your local machine, CI/CD machines or nodes, and other private network configurations. In this guide you will learn how to :

  1. Setup your environment
  2. Upload your app
  3. Configure and run your Local test
  4. View test execution results

1. Setup your environment

  • You will need a BrowserStack username and access_key. If you haven’t created an account yet, sign up for a free trial or purchase a paid plan. After signup, you can obtain your access credentials here
  • Ensure you have Node.js 8.11.2+ installed on your system. You can download updated Node version from nodejs.org
  • You will need access to your Android app (.apk or .aab file) or iOS app (.ipa file)
Note: If you do not have an .apk or .ipa file and are looking to simply try App Automate Local Testing, you can download and test using our sample Android Local app or sample iOS Local app.

2. Upload your app

Upload your Android app (.apk or .aab file) or iOS app (.ipa file) to BrowserStack servers using our REST API. Here is an example cURL request to upload app on App Automate :

curl -u "YOUR_USERNAME:YOUR_ACCESS_KEY" \
-X POST "https://api-cloud.browserstack.com/app-automate/upload" \
-F "file=@/path/to/apk/file"
curl -u "YOUR_USERNAME:YOUR_ACCESS_KEY" ^
-X POST "https://api-cloud.browserstack.com/app-automate/upload" ^
-F "file=@/path/to/apk/file"

Ensure that @ symbol is prepended to the file path in the above request. A sample response for the above request is shown below:

{
    "app_url" : "bs://j3c874f21852ba57957a3fdc33f47514288c4ba4"
}

Please note the app_url value returned in the API response (bs://j3c874..... in the above example). We will use this value to set the application under test while configuring the test later on.

Note:
  1. App upload will take a few seconds to about a minute depending on the size of your app. Do not interrupt the cURL command until you get the response back.
  2. If you upload an iOS app, we will re-sign the app with our own provisioning profile to be able to install your app on our devices during test execution.

3. Configure and run your Local test

Setup your project

Clone the WebdriverIO sample integration code from our GitHub repository.

git clone https://github.com/browserstack/webdriverio-appium-app-browserstack.git

Next, execute the following commands in project’s base directory to install the required dependencies:

# Test an android app
cd android
npm i

# Test an iOS app
cd ios
npm i

This will install requisite dependencies including WebdriverIO package :

//...
  "dependencies": {
    "@wdio/cli": "^5.20.1",
    "@wdio/local-runner": "^5.20.1",
    "@wdio/mocha-framework": "^5.18.7",
    "browserstack-local": "^1.4.5"
  }
//...

Configure Appium’s desired capabilities

Desired capabilities are a series of key-value pairs that allow you to configure your Appium tests on BrowserStack. The following capabilities are required for Local Testing :

  • app capability : Its used to specify your uploaded app that will be installed on the device during test execution. Use the app_url obtained in Upload your App section to set its value.
  • device capability : Its used to specify the BrowserStack device you want to run the test on.
  • browserstack.local capability : Its used to enable BrowserStack Local feature for your test execution.

In the WebdriverIO sample integration code, Appium’s desired capabilities are defined in the local.conf.js file located in the examples/run-local-test directory :


var browserstack = require('browserstack-local');

exports.config = {
  user: process.env.BROWSERSTACK_USERNAME || 'YOUR_USERNAME',
  key: process.env.BROWSERSTACK_ACCESS_KEY || 'YOUR_ACCESS_KEY',

  //...

  capabilities: [{
    project: "First Webdriverio Android Project",
    build: 'Webdriverio Android Local',
    name: 'local_test',
    device: 'Google Pixel 3',
    os_version: "9.0",
    app: process.env.BROWSERSTACK_APP_ID || 'bs://<app-id>',
    'browserstack.local': true,
    'browserstack.debug': true
  }],

  //...

};


var browserstack = require('browserstack-local');

exports.config = {
  user: process.env.BROWSERSTACK_USERNAME || 'YOUR_USERNAME',
  key: process.env.BROWSERSTACK_ACCESS_KEY || 'YOUR_ACCESS_KEY',

  //...

  capabilities: [{
    project: "First Webdriverio iOS Project",
    build: 'Webdriverio iOS Local',
    name: 'local_test',
    device: 'iPhone 11 Pro',
    os_version: "13",
    app: process.env.BROWSERSTACK_APP_ID || 'bs://<app-id>',
    'browserstack.local': true,
    'browserstack.debug': true
  }],

  //...

};

Note:

Establish a Local Testing connection

In addition to using the browserstack.local capability, you also need to establish a Local Testing connection from your local or CI/CD machine to BrowserStack servers. Within your test scripts, you can add a code snippet that will automatically start and stop Local Testing connection using BrowserStack’s NodeJs binding for BrowserStack Local.

In the WebdriverIO sample integration code, the Local Testing connection is initialised in the local.conf.js file located in the examples/run-local-testdirectory as shown below :


//...

// Code to start browserstack local before start of test
  onPrepare: (config, capabilities) => {
    console.log("Connecting local");
    return new Promise( (resolve, reject) => {
      exports.bs_local = new browserstack.Local();
      exports.bs_local.start({'key': exports.config.key }, (error) => {
        if (error) return reject(error);
        console.log('Connected. Now testing...');
        resolve();
      });
    });
  },

  // Code to stop browserstack local after end of test
  onComplete: (capabilties, specs) => {
    console.log("Closing local tunnel");
    return new Promise( (resolve, reject) => {
      exports.bs_local.stop( (error) => {
        if (error) return reject(error);
        console.log("Stopped BrowserStackLocal");
        resolve();
      });
    });
  }

  //...

Create remote Webdriver

Once you have configured desired capabilities and established Local Testing connection, you can initialize an Appium webdriver to test remotely on BrowserStack. In order to do so, provide your BrowserStack access credentials in user and key parameters and our WebdriverIO integration will automatically initialize the remote webdriver with your access credentials set in the config file.

In the WebdriverIO sample integration code, Appium’s desired capabilities are defined in the local.conf.js file located in the examples/run-local-test directory :

//...

exports.config = {
  user: process.env.BROWSERSTACK_USERNAME || 'YOUR_USERNAME',
  key: process.env.BROWSERSTACK_ACCESS_KEY || 'YOUR_ACCESS_KEY',

//...

Setup your test-case

This step will help you setup your first Local Testing test case with WebdriverIO framework. In the WebdriverIO sample integration code, we have provided a sample test-case in examples/run-local-test/specs directory for BrowserStack’s sample apps. If you are testing your own app, please modify the test case accordingly.

If you are using your own app, modify the following code as per your test case:

var path = require('path');
var assert = require('assert');

describe('BrowserStack Local Testing', () => {
  it('can check tunnel working', async () => {
    var searchSelector = 
    await $('android=new UiSelector().resourceId(
      "com.example.android.basicnetworking:id/test_action")');
    await searchSelector.waitForDisplayed({ timeout: 30000 });
    await searchSelector.click();

    var insertTextSelector = await $(`android.widget.TextView`);
    await insertTextSelector.waitForDisplayed({ timeout: 30000 });

    var testElement = null;

    try {
      var textElement =
      await $('android=new UiSelector().textContains("active connection is")');
      await textElement.waitForDisplayed({ timeout: 30000 });
      testElement = textElement;
    }
    catch {
      var screenshotPath = path.resolve(__dirname, 'screenshot.png');
      await browser.saveScreenshot(screenshotPath);
      console.log('Screenshot stored at ' + screenshotPath);
      throw new Error('Cannot find the needed TextView element from app');
    }

    var matchedString = await testElement.getText();
    console.log(matchedString);
    assert(matchedString.indexOf('The active connection is wifi') !== -1);
    assert(matchedString.indexOf('Up and running') !== -1);
  });

If you are using your own app, modify the following code as per your test case:

var path = require('path');
var assert = require('assert');

describe('BrowserStack Local Testing', () => {
  it('can check tunnel working', async () => {
    var searchSelector = await $(`~Test BrowserStackLocal connection`);
    await searchSelector.waitForDisplayed({ timeout: 30000 });
    await searchSelector.click();

    var textElements = await $(`~ResultBrowserStackLocal`);
    await textElements.waitForDisplayed({ timeout: 30000 });

    var testElement = null;

    var textContent = await textElements.getText();
    if (textContent.indexOf('Up and running') !== -1) {
      testElement = textElements;
    }

    if (testElement === null) {
      var screenshotPath = path.resolve(__dirname, 'screenshot.png');
      await browser.saveScreenshot(screenshotPath);
      console.log('Screenshot stored at ' + screenshotPath);
      throw new Error('Cannot find the Up and running response');
    }

    var matchedString = await testElement.getText();
    assert(matchedString == 'Response is: Up and running');
  });
});

Run the test

You are ready to run your first local test on BrowserStack. In the WebdriverIO sample integration code, switch to android/ or ios/ directory, and run the test using command :

# Run using npm
npm run local

4. View test execution results

You can access the test execution results, and debugging information such as video recording, network and device logs on App Automate dashboard or using our REST APIs.

What’s next

Congratulations! You just ran your first local test on App Automate. Next, you can learn to :

  • Run tests in parallel - Speed up test execution by running tests simultaneously across multiple BrowserStack devices

Need some help?

If you have any queries, please get in touch with us.

We're sorry to hear that. Please share your feedback so we can do better






Contact our Support team for immediate help while we work on improving our docs.

We're continuously improving our docs. We'd love to know what you liked





Thank you for your valuable feedback

Is this page helping you?

Yes
No

We're sorry to hear that. Please share your feedback so we can do better






Contact our Support team for immediate help while we work on improving our docs.

We're continuously improving our docs. We'd love to know what you liked





Thank you for your valuable feedback!

Talk to automation expert