fix: interrupt request.allHeaders()/response() on page.close() (#27695)
Reference https://github.com/microsoft/playwright/issues/27227
This commit is contained in:
parent
5752a28f87
commit
5e51a734e7
|
|
@ -20,7 +20,7 @@ import type * as frames from './frames';
|
||||||
import type * as types from './types';
|
import type * as types from './types';
|
||||||
import type * as channels from '@protocol/channels';
|
import type * as channels from '@protocol/channels';
|
||||||
import { assert } from '../utils';
|
import { assert } from '../utils';
|
||||||
import { ManualPromise } from '../utils/manualPromise';
|
import { LongStandingScope, ManualPromise } from '../utils/manualPromise';
|
||||||
import { SdkObject } from './instrumentation';
|
import { SdkObject } from './instrumentation';
|
||||||
import type { HeadersArray, NameValue } from '../common/types';
|
import type { HeadersArray, NameValue } from '../common/types';
|
||||||
import { APIRequestContext } from './fetch';
|
import { APIRequestContext } from './fetch';
|
||||||
|
|
@ -129,6 +129,10 @@ export class Request extends SdkObject {
|
||||||
this._isFavicon = url.endsWith('/favicon.ico') || !!redirectedFrom?._isFavicon;
|
this._isFavicon = url.endsWith('/favicon.ico') || !!redirectedFrom?._isFavicon;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private _targetClosedScope(): LongStandingScope {
|
||||||
|
return this._serviceWorker?.openScope || this._frame?._page.openScope || new LongStandingScope();
|
||||||
|
}
|
||||||
|
|
||||||
_setFailureText(failureText: string) {
|
_setFailureText(failureText: string) {
|
||||||
this._failureText = failureText;
|
this._failureText = failureText;
|
||||||
this._waitForResponsePromise.resolve(null);
|
this._waitForResponsePromise.resolve(null);
|
||||||
|
|
@ -179,11 +183,11 @@ export class Request extends SdkObject {
|
||||||
}
|
}
|
||||||
|
|
||||||
async rawRequestHeaders(): Promise<HeadersArray> {
|
async rawRequestHeaders(): Promise<HeadersArray> {
|
||||||
return this._overrides?.headers || this._rawRequestHeadersPromise;
|
return this._overrides?.headers || this._targetClosedScope().race(this._rawRequestHeadersPromise);
|
||||||
}
|
}
|
||||||
|
|
||||||
response(): PromiseLike<Response | null> {
|
response(): PromiseLike<Response | null> {
|
||||||
return this._waitForResponsePromise;
|
return this._targetClosedScope().race(this._waitForResponsePromise);
|
||||||
}
|
}
|
||||||
|
|
||||||
_existingResponse(): Response | null {
|
_existingResponse(): Response | null {
|
||||||
|
|
|
||||||
|
|
@ -17,6 +17,7 @@
|
||||||
|
|
||||||
import type { ServerResponse } from 'http';
|
import type { ServerResponse } from 'http';
|
||||||
import { test as it, expect } from './pageTest';
|
import { test as it, expect } from './pageTest';
|
||||||
|
import { kTargetClosedErrorMessage } from '../config/errors';
|
||||||
|
|
||||||
it('Page.Events.Request @smoke', async ({ page, server }) => {
|
it('Page.Events.Request @smoke', async ({ page, server }) => {
|
||||||
const requests = [];
|
const requests = [];
|
||||||
|
|
@ -137,3 +138,23 @@ it('should resolve responses after a navigation', async ({ page, server, browser
|
||||||
// the response should resolve to null, because the page navigated.
|
// the response should resolve to null, because the page navigated.
|
||||||
expect(await responsePromise).toBe(null);
|
expect(await responsePromise).toBe(null);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('interrupt request.response() and request.allHeaders() on page.close', async ({ page, server, browserName }) => {
|
||||||
|
it.info().annotations.push({ type: 'issue', description: 'https://github.com/microsoft/playwright/issues/27227' });
|
||||||
|
server.setRoute('/one-style.css', (req, res) => {
|
||||||
|
res.setHeader('Content-Type', 'text/css');
|
||||||
|
});
|
||||||
|
const reqPromise = page.waitForRequest('**/one-style.css');
|
||||||
|
await page.goto(server.PREFIX + '/one-style.html', { waitUntil: 'domcontentloaded' });
|
||||||
|
const req = await reqPromise;
|
||||||
|
const respPromise = req.response().catch(e => e);
|
||||||
|
const headersPromise = req.allHeaders().catch(e => e);
|
||||||
|
await page.close();
|
||||||
|
expect((await respPromise).message).toContain(kTargetClosedErrorMessage);
|
||||||
|
// All headers are the same as "provisional" headers in Firefox.
|
||||||
|
if (browserName === 'firefox')
|
||||||
|
expect((await headersPromise)['user-agent']).toBeTruthy();
|
||||||
|
else
|
||||||
|
expect((await headersPromise).message).toContain(kTargetClosedErrorMessage);
|
||||||
|
|
||||||
|
});
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue