fix: `exposeBinding` should work in parallel

This commit is contained in:
Simon Knott 2025-10-06 14:28:03 +02:00
parent 30ddf7ad6b
commit dc209d2e7a
No known key found for this signature in database
GPG Key ID: 8CEDC00028084AEC
2 changed files with 22 additions and 11 deletions

View File

@ -93,7 +93,7 @@ export abstract class BrowserContext extends SdkObject {
_closeReason: string | undefined;
readonly clock: Clock;
_clientCertificatesProxy: ClientCertificatesProxy | undefined;
private _playwrightBindingExposed = false;
private _playwrightBindingExposed?: Promise<void>;
readonly dialogManager: DialogManager;
constructor(browser: Browser, options: types.BrowserContextOptions, browserContextId: string | undefined) {
@ -304,19 +304,19 @@ export abstract class BrowserContext extends SdkObject {
}
async exposePlaywrightBindingIfNeeded() {
if (this._playwrightBindingExposed)
return;
this._playwrightBindingExposed = true;
await this.doExposePlaywrightBinding();
this._playwrightBindingExposed ??= (async () => {
await this.doExposePlaywrightBinding();
this.bindingsInitScript = PageBinding.createInitScript();
this.initScripts.push(this.bindingsInitScript);
await this.doAddInitScript(this.bindingsInitScript);
await this.safeNonStallingEvaluateInAllFrames(this.bindingsInitScript.source, 'main');
this.bindingsInitScript = PageBinding.createInitScript();
this.initScripts.push(this.bindingsInitScript);
await this.doAddInitScript(this.bindingsInitScript);
await this.safeNonStallingEvaluateInAllFrames(this.bindingsInitScript.source, 'main');
})();
return await this._playwrightBindingExposed;
}
needsPlaywrightBinding() {
return this._playwrightBindingExposed;
needsPlaywrightBinding(): boolean {
return this._playwrightBindingExposed !== undefined;
}
async exposeBinding(progress: Progress, name: string, needsHandle: boolean, playwrightBinding: frames.FunctionWithSource, forClient?: unknown): Promise<PageBinding> {

View File

@ -292,3 +292,14 @@ it('should fail with busted Array.prototype.toJSON', async ({ page }) => {
expect.soft(await page.evaluate(() => ([] as any).toJSON())).toBe('"[]"');
});
it('exposeBinding should work in parallel', { annotation: { type: 'issue', description: 'https://github.com/microsoft/playwright/issues/37712' } }, async ({ page }) => {
await Promise.all([
page.exposeBinding('foo', () => 42),
page.exposeBinding('bar', () => 42),
]);
await page.evaluate(() => {
(window as any).foo();
(window as any).bar();
});
});