Enable GPU to speed up slow Playwright tests in headless mode

When I wrote end-to-end tests for Sudocle the other day, I no­ticed that they ran much faster when I star­ted my browser in non-head­less mode. After some de­bug­ging, I was able to fig­ure out that the browser I was us­ing to run my tests (Chrome/​Chro­mium), auto­mat­ic­ally em­ploys a soft­ware ren­derer for WebGL when star­ted head­less. Since Sudocle heav­ily re­lies on WebGL, the tests could be­ne­fit a great deal from hard­ware ac­cel­er­a­tion.

tl;dr

To force-en­able GPU hard­ware ac­cel­er­a­tion for head­less Chrome/​Chro­mium, you have to run it with --use-gl=desktop or --use-gl=egl. You can add this para­meter in your playwright.config.js file:

const config = {
  use: {
    channel: "chrome",
    launchOptions: {
      // force GPU hardware acceleration
      // (even in headless mode)
      args: ["--use-gl=egl"]
    }
  }
}

module.exports = config

Whether you need to use desktop or egl, seems to de­pend on the en­vir­on­ment or op­er­at­ing sys­tem you’re on. For me, on ma­cOS, egl worked well. To check if hard­ware ac­cel­er­a­tion is en­abled or not, you can use the code be­low.

Benchmark

With hard­ware ac­cel­er­a­tion en­abled, I was able to re­duce the av­er­age runtime of my tests from 1.9s to 1.3s on my Mac­Book. De­pend­ing on how many tests you run and how com­plex they are, your test suite can take sev­eral minutes less than without hard­ware ac­cel­er­a­tion.

In my case, at the time of writ­ing, I’m run­ning 823 tests with 6 work­ers. Without hard­ware ac­cel­er­a­tion, the test suite took 4m 19s. Now, it only takes 2m 59s.

You can find the source code of my tests here:

https://github.com/michel-kraemer/sudocle/blob/main/tests/Grid.spec.js

My playwright.config.js can be found here:

https://github.com/michel-kraemer/sudocle/blob/main/playwright.config.js

Please note that the test fix­tures are not checked in to the source code re­pos­it­ory of Sudocle.

Checking if hardware acceleration is enabled

If you want to check if your head­less browser has GPU hard­ware ac­cel­er­a­tion en­abled or not, you can use the fol­low­ing test:

test("GPU hardware acceleration", async ({ page }) => {
  await page.goto("chrome://gpu")
  let featureStatusList = page.locator(".feature-status-list")
  await expect(featureStatusList).toContainText("Hardware accelerated")
})

Happy test­ing!


Posted by Michel Krämer
on January, 2nd 2022.