Version
1.63.0
Steps to reproduce
- Run a suite of ~90 short tests per worker on Windows with the Firefox project (3 workers,
fullyParallel: true).
- Record traces with
--trace on.
- Measure the duration of the
Close context step (fixture teardown) in each test's test.trace.
Expected behavior
browserContext.close() takes a few tens of milliseconds, independent of how many contexts the browser process has closed before.
Actual behavior
Close context takes 0.03 s (median) but jumps to 7–17 s on exactly every 10th context closed by a worker (positions 10, 20, 30, … in the worker's test order), and the cost grows with the age of the browser process.
Measured Close context durations at every 10th close, per worker (seconds; 262 tests, 3 workers, Windows 11):
w0: 1.8, 9.0, 13.5, 14.1, 13.6, 15.9, 14.4, 16.5, 6.7
w1: 2.2, 8.1, 10.3, 9.6, 15.6, 15.2, 15.9, 12.2
w2: 2.4, 8.5, 10.6, 11.4, 14.3, 16.7, 15.1, 13.7, 9.7
All other closes are < 0.5 s. Create context / create page / navigation are unaffected. Over a 10-minute Firefox-only run this adds ~290 s of worker time (~16 %).
The source is browser_patches/firefox/juggler/TargetRegistry.js, BrowserContext.destroy():
// Clean the memory. on every 10'th context closure. On M1 Max, this method
// takes ~150ms, so we spread them out.
if (++globalContextCloseCounter % 10 === 0) {
await new Promise(x => {
Cc["@mozilla.org/memory-reporter-manager;1"]
.getService(Ci.nsIMemoryReporterManager)
.minimizeMemoryUsage(x);
});
}
On Windows the awaited minimizeMemoryUsage() is two orders of magnitude slower than the 150 ms noted in the comment, and because it is awaited inside Browser.removeBrowserContext, the test runner's worker is blocked for the whole duration. Setting browser.cache.disk.enable: false in firefoxUserPrefs reduces the stall by roughly 40 % (3.9–11.7 s instead of 8–17 s), which suggests cache trimming is part of the cost, but the growth with process age remains.
Would it be possible to not await minimizeMemoryUsage() on the removeBrowserContext path (or to make the periodic cleanup opt-in / configurable)?
Additional context
No response
Environment
- OS: Windows 11
- Firefox: Playwright build for 1.63.0 (Firefox 155.0)
- Node.js: 24.x
- 3 workers, `fullyParallel: true`, `trace: on` (also reproduced with `retain-on-failure`)
Version
1.63.0
Steps to reproduce
fullyParallel: true).--trace on.Close contextstep (fixture teardown) in each test'stest.trace.Expected behavior
browserContext.close()takes a few tens of milliseconds, independent of how many contexts the browser process has closed before.Actual behavior
Close contexttakes 0.03 s (median) but jumps to 7–17 s on exactly every 10th context closed by a worker (positions 10, 20, 30, … in the worker's test order), and the cost grows with the age of the browser process.Measured
Close contextdurations at every 10th close, per worker (seconds; 262 tests, 3 workers, Windows 11):All other closes are < 0.5 s. Create context / create page / navigation are unaffected. Over a 10-minute Firefox-only run this adds ~290 s of worker time (~16 %).
The source is
browser_patches/firefox/juggler/TargetRegistry.js,BrowserContext.destroy():On Windows the awaited
minimizeMemoryUsage()is two orders of magnitude slower than the 150 ms noted in the comment, and because it is awaited insideBrowser.removeBrowserContext, the test runner's worker is blocked for the whole duration. Settingbrowser.cache.disk.enable: falseinfirefoxUserPrefsreduces the stall by roughly 40 % (3.9–11.7 s instead of 8–17 s), which suggests cache trimming is part of the cost, but the growth with process age remains.Would it be possible to not await
minimizeMemoryUsage()on theremoveBrowserContextpath (or to make the periodic cleanup opt-in / configurable)?Additional context
No response
Environment