Menu

Important: This documentation is about an older version. It's relevant only to the release noted, many of the features and functions have been updated or replaced. Please view the current version.

Open source

Migrating to k6 v0.46

This guide outlines the key changes you will need to make when moving your existing k6 browser test scripts to the new k6 browser module (bundled with k6 version 0.46).

Key changes

The updated version introduces notable structural changes in its operation and API, including breaking changes:

Note

You no longer need to use the K6_BROWSER_ENABLED flag when running browser tests with the k6 command.

Before and after comparison

Let’s start with an overview of the main differences between the previous and new versions of the k6 browser API.

JavaScript
import { chromium } from 'k6/experimental/browser';

export default async function () {
  const browser = chromium.launch({
    headless: false,
    timeout: '60s',
  });
  const page = browser.newPage();

  try {
    await page.goto('https://test.k6.io/');
    page.screenshot({ path: 'screenshot.png' });
  } finally {
    page.close();
    browser.close();
  }
}
JavaScript
import { browser } from 'k6/experimental/browser';

export const options = {
  scenarios: {
    ui: {
      executor: 'shared-iterations',
      options: {
        browser: {
          type: 'chromium',
        },
      },
    },
  },
};

export default async function () {
  const page = browser.newPage();

  try {
    await page.goto('https://test.k6.io/');
    page.screenshot({ path: 'screenshot.png' });
  } finally {
    page.close();
  }
}

Import path

With the browser type (specifically chromium) now set in scenario options, you should directly import the browser object from the browser module.

JavaScript
import { chromium } from 'k6/experimental/browser';
JavaScript
import { browser } from 'k6/experimental/browser';

Simplified resource management

The browser lifecycle is now automatically managed by the browser module, and so the chromium.launch(), chromium.connect(), and browser.close() methods are no longer necessary and have been removed.

Now, all that is needed is to specify the browser.type within the scenario options. If the option is set, a browser instance will automatically start at the beginning and close at the end of each test iteration.

Browser options

With the removal of the chromium.launch() and chromium.connect() methods, setting browsers options is now done by using environment variables. For more information, refer to Browser Module Options.

Launching a browser

Before:

JavaScript
export default async function () {
  const browser = chromium.launch({
    headless: false,
    timeout: '60s',
  });
}

After:

bash
$ K6_BROWSER_HEADLESS=false K6_BROWSER_TIMEOUT='60s' k6 run script.js
docker
# WARNING!
# The grafana/k6:master-with-browser image launches a Chrome browser by setting the
# 'no-sandbox' argument. Only use it with trustworthy websites.
#
# As an alternative, you can use a Docker SECCOMP profile instead, and overwrite the
# Chrome arguments to not use 'no-sandbox' such as:
# docker container run --rm -i -e K6_BROWSER_ARGS='' --security-opt seccomp=$(pwd)/chrome.json grafana/k6:master-with-browser run - <script.js
#
# You can find an example of a hardened SECCOMP profile in:
# https://raw.githubusercontent.com/jfrazelle/dotfiles/master/etc/docker/seccomp/chrome.json.
docker run --rm -i -e K6_BROWSER_HEADLESS=false -e K6_BROWSER_TIMEOUT='60s' grafana/k6:master-with-browser run - <script.js
windows
C:\k6> set "K6_BROWSER_HEADLESS=false" && set "K6_BROWSER_TIMEOUT='60s' " && k6 run script.js
powershell
PS C:\k6> $env:K6_BROWSER_HEADLESS="false" ; $env:K6_BROWSER_TIMEOUT='60s' ; k6 run script.js

Connecting to a remote browser

Before:

JavaScript
export default async function () {
  const remoteURL = 'REMOTE_URL';
  const browser = chromium.connect(remoteURL);
  const page = browser.newPage();
}

After:

bash
$ K6_BROWSER_WS_URL='REMOTE_URL' k6 run script.js
docker
# WARNING!
# The grafana/k6:master-with-browser image launches a Chrome browser by setting the
# 'no-sandbox' argument. Only use it with trustworthy websites.
#
# As an alternative, you can use a Docker SECCOMP profile instead, and overwrite the
# Chrome arguments to not use 'no-sandbox' such as:
# docker container run --rm -i -e K6_BROWSER_ARGS='' --security-opt seccomp=$(pwd)/chrome.json grafana/k6:master-with-browser run - <script.js
#
# You can find an example of a hardened SECCOMP profile in:
# https://raw.githubusercontent.com/jfrazelle/dotfiles/master/etc/docker/seccomp/chrome.json.
docker run --rm -i -e K6_BROWSER_WS_URL='REMOTE_URL' grafana/k6:master-with-browser run - <script.js
windows
C:\k6> set "K6_BROWSER_WS_URL='REMOTE_URL'" && set "K6_BROWSER_TIMEOUT='60s' && k6 run script.js
powershell
PS C:\k6> $env:K6_BROWSER_WS_URL='REMOTE_URL' ; k6 run script.js

Note

The following browser options are no longer supported: devtools, env, and proxy since they weren’t providing much value. slowMo has been temporarily removed, and we’re working on reintroducing it.

Scenario options

You must now set the executor and browser type as options in a scenario definition. Specifically, the browser.type option should be set to chromium, as Chromium is the only browser supported.

JavaScript
export const options = {
  scenarios: {
    ui: {
      executor: 'shared-iterations',
      options: {
        browser: {
          type: 'chromium',
        },
      },
    },
  },
};

Opening and closing a page

You can open a new page by using the imported browser object’s browser.newPage() method. You can still use the Page object as before.

JavaScript
export default async function () {
  const browser = chromium.launch();
  const page = browser.newPage();
  // ...
  page.close();
  browser.close();
}
JavaScript
export default async function () {
  const page = browser.newPage();
  // ...
  page.close();
}

The browser.close() method has been removed, so you can remove that from your scripts and use page.close() once you’re done using the page object.

Note

Closing of the page is critical for the calculation of accurate Web Vital metrics. See the browser metrics for more details.

Browser context limit

The new browser implementation limits the usage to a single active BrowserContext per iteration. This change enhances the prediction of resource requirements for a test run and promotes the use of scenarios to separate independent browser sessions.

For instance, the code below will not function as intended, as it attempts to execute two simultaneous BrowserContexts within the same iteration.

JavaScript
export default async function () {
  const context1 = browser.newContext();
  // Simultaneous browser contexts are not permitted!
  const context2 = browser.newContext();
}

On the other hand, the next example will function correctly by closing the initial BrowserContext prior to establishing a new one.

JavaScript
export default async function () {
  const context1 = browser.newContext();
  context1.close();

  // Since the first browser context is closed, a new browser context can be created.
  const context2 = browser.newContext();
  context2.close();
}

These updates make the usage of the API more straightforward for users, aiding in more consistent and automatic resource management.

For all the details, make sure to review the complete changelog for k6 version 0.46. For more information watch k6 Office Hours #98, where we discuss the latest changes in k6 browser, and, as always, ask in the community forum if you need help!