diff --git a/src/server/supplements/har/harTracer.ts b/src/server/supplements/har/harTracer.ts
index eded5c3e95..2390c5607d 100644
--- a/src/server/supplements/har/harTracer.ts
+++ b/src/server/supplements/har/harTracer.ts
@@ -133,9 +133,6 @@ export class HarTracer {
}
private _onRequest(request: network.Request) {
- if (this._options.skipScripts && request.resourceType() === 'script')
- return;
-
const page = request.frame()._page;
const url = network.parsedURL(request.url());
if (!url)
@@ -228,6 +225,11 @@ export class HarTracer {
this._addBarrier(page, compressionCalculationBarrier.barrier);
const promise = response.body().then(buffer => {
+ if (this._options.skipScripts && request.resourceType() === 'script') {
+ compressionCalculationBarrier.setDecodedBodySize(0);
+ return;
+ }
+
const content = harEntry.response.content;
content.size = buffer.length;
compressionCalculationBarrier.setDecodedBodySize(buffer.length);
diff --git a/src/web/traceViewer/ui/networkResourceDetails.tsx b/src/web/traceViewer/ui/networkResourceDetails.tsx
index bbc24afdcc..431e98ae80 100644
--- a/src/web/traceViewer/ui/networkResourceDetails.tsx
+++ b/src/web/traceViewer/ui/networkResourceDetails.tsx
@@ -101,6 +101,11 @@ export const NetworkResourceDetails: React.FunctionComponent<{
const requestContentType = requestContentTypeHeader ? requestContentTypeHeader.value : '';
const resourceName = resource.request.url.substring(resource.request.url.lastIndexOf('/') + 1);
+ let contentType = resource.response.content.mimeType;
+ const charset = contentType.match(/^(.*);\s*charset=.*$/);
+ if (charset)
+ contentType = charset[1];
+
return
setSelected(index)}>
{resource.response.status}
{resource.request.method}
{resourceName}
- {resource.response.content.mimeType}
+ {contentType}
} body={
diff --git a/tests/trace-viewer/trace-viewer.spec.ts b/tests/trace-viewer/trace-viewer.spec.ts
index 0e4b60191a..3c4c575a10 100644
--- a/tests/trace-viewer/trace-viewer.spec.ts
+++ b/tests/trace-viewer/trace-viewer.spec.ts
@@ -26,6 +26,7 @@ class TraceViewerPage {
consoleLineMessages: Locator;
consoleStacks: Locator;
stackFrames: Locator;
+ networkRequests: Locator;
constructor(public page: Page) {
this.actionTitles = page.locator('.action-title');
@@ -34,6 +35,7 @@ class TraceViewerPage {
this.consoleLineMessages = page.locator('.console-line-message');
this.consoleStacks = page.locator('.console-stack');
this.stackFrames = page.locator('.stack-trace-frame');
+ this.networkRequests = page.locator('.network-request-title');
}
async actionIconsText(action: string) {
@@ -62,6 +64,10 @@ class TraceViewerPage {
await this.page.click('text="Source"');
}
+ async showNetworkTab() {
+ await this.page.click('text="Network"');
+ }
+
async eventBars() {
await this.page.waitForSelector('.timeline-bar.event:visible');
const list = await this.page.$$eval('.timeline-bar.event:visible', ee => ee.map(e => e.className));
@@ -98,7 +104,7 @@ const test = playwrightTest.extend<{ showTraceViewer: (trace: string) => Promise
let traceFile: string;
-test.beforeAll(async function recordTrace({ browser, browserName, browserType }, workerInfo) {
+test.beforeAll(async function recordTrace({ browser, browserName, browserType, server }, workerInfo) {
const context = await browser.newContext();
await context.tracing.start({ name: 'test', screenshots: true, snapshots: true });
const page = await context.newPage();
@@ -125,7 +131,7 @@ test.beforeAll(async function recordTrace({ browser, browserName, browserType },
await Promise.all([
page.waitForNavigation(),
- page.waitForTimeout(200).then(() => page.goto('data:text/html,Hello world 2'))
+ page.waitForTimeout(200).then(() => page.goto(server.PREFIX + '/frames/frame.html'))
]);
await page.setViewportSize({ width: 500, height: 600 });
@@ -153,7 +159,7 @@ test('should open simple trace viewer', async ({ showTraceViewer }) => {
/page.evaluate— \d+ms/,
/page.click"Click"— \d+ms/,
/page.waitForNavigation— \d+ms/,
- /page.gotodata:text\/html,Hello world 2<\/html>— \d+ms/,
+ /page.gotohttp:\/\/localhost:\d+\/frames\/frame.html— \d+ms/,
/page.setViewportSize— \d+ms/,
/page.hoverbody— \d+ms/,
]);
@@ -233,3 +239,14 @@ test('should have correct stack trace', async ({ showTraceViewer }) => {
'BrowserType.browserType._onWillCloseContext trace-viewer.spec.ts :XXX',
]);
});
+
+test('should have network requests', async ({ showTraceViewer }) => {
+ const traceViewer = await showTraceViewer(traceFile);
+ await traceViewer.selectAction('http://localhost');
+ await traceViewer.showNetworkTab();
+ await expect(traceViewer.networkRequests).toHaveText([
+ '200GETframe.htmltext/html',
+ '200GETstyle.csstext/css',
+ '200GETscript.jsapplication/javascript',
+ ]);
+});
diff --git a/tests/tracing.spec.ts b/tests/tracing.spec.ts
index 716c6fd175..1cebe09f3d 100644
--- a/tests/tracing.spec.ts
+++ b/tests/tracing.spec.ts
@@ -43,9 +43,13 @@ test('should collect trace with resources, but no js', async ({ context, page, s
expect(events.find(e => e.metadata?.apiName === 'page.close')).toBeTruthy();
expect(events.some(e => e.type === 'frame-snapshot')).toBeTruthy();
- expect(events.some(e => e.type === 'resource-snapshot' && e.snapshot.request.url.endsWith('style.css'))).toBeTruthy();
- expect(events.some(e => e.type === 'resource-snapshot' && e.snapshot.request.url.endsWith('script.js'))).toBeFalsy();
expect(events.some(e => e.type === 'screencast-frame')).toBeTruthy();
+ const style = events.find(e => e.type === 'resource-snapshot' && e.snapshot.request.url.endsWith('style.css'));
+ expect(style).toBeTruthy();
+ expect(style.snapshot.response.content._sha1).toBeTruthy();
+ const script = events.find(e => e.type === 'resource-snapshot' && e.snapshot.request.url.endsWith('script.js'));
+ expect(script).toBeTruthy();
+ expect(script.snapshot.response.content._sha1).toBe(undefined);
});
test('should not collect snapshots by default', async ({ context, page, server }, testInfo) => {