diff --git a/packages/html-reporter/src/links.tsx b/packages/html-reporter/src/links.tsx index 8c1dcc85dc..935b77f7b5 100644 --- a/packages/html-reporter/src/links.tsx +++ b/packages/html-reporter/src/links.tsx @@ -76,7 +76,8 @@ export const AttachmentLink: React.FunctionComponent<{ href?: string, linkName?: string, openInNewTab?: boolean, -}> = ({ attachment, href, linkName, openInNewTab }) => { + depth?: number, +}> = ({ attachment, href, linkName, openInNewTab, depth }) => { return {attachment.contentType === kMissingContentType ? icons.warning() : icons.attachment()} {attachment.path && {linkName || attachment.name}} @@ -87,7 +88,7 @@ export const AttachmentLink: React.FunctionComponent<{ )} } loadChildren={attachment.body ? () => { return [
{linkifyText(attachment.body!)}
]; - } : undefined} depth={0} style={{ lineHeight: '32px' }}>
; + } : undefined} depth={depth ?? 0} style={{ lineHeight: '32px' }}>; }; function downloadFileNameForAttachment(attachment: TestAttachment): string { diff --git a/packages/html-reporter/src/testResultView.tsx b/packages/html-reporter/src/testResultView.tsx index 8ee36d0cda..f3354064eb 100644 --- a/packages/html-reporter/src/testResultView.tsx +++ b/packages/html-reporter/src/testResultView.tsx @@ -98,7 +98,7 @@ export const TestResultView: React.FC<{ {result.errors.map((error, index) => )} } {!!result.steps.length && - {result.steps.map((step, i) => )} + {result.steps.map((step, i) => )} } {diffs.map((diff, index) => @@ -148,7 +148,15 @@ export const TestResultView: React.FC<{ const StepTreeItem: React.FC<{ step: TestStep; depth: number, -}> = ({ step, depth }) => { + attachments: TestAttachment[], +}> = ({ step, depth, attachments }) => { + if (step.category === 'attach') { + const attachmentName = step.title.match(/^attach "(.*)"$/)?.[1]; + const attachment = attachments.find(a => a.name === attachmentName); + if (attachment) + return ; + } + return {msToString(step.duration)} {statusIcon(step.error || step.duration === -1 ? 'failed' : 'passed')} @@ -156,7 +164,7 @@ const StepTreeItem: React.FC<{ {step.count > 1 && <> ✕ {step.count}} {step.location && — {step.location.file}:{step.location.line}} } loadChildren={step.steps.length + (step.snippet ? 1 : 0) ? () => { - const children = step.steps.map((s, i) => ); + const children = step.steps.map((s, i) => ); if (step.snippet) children.unshift(); return children; diff --git a/packages/html-reporter/src/types.ts b/packages/html-reporter/src/types.ts index 733e88e8b9..ea2cf453bc 100644 --- a/packages/html-reporter/src/types.ts +++ b/packages/html-reporter/src/types.ts @@ -102,6 +102,7 @@ export type TestResult = { export type TestStep = { title: string; + category: 'hook' | 'fixture' | 'test.step' | 'expect' | 'attach' | string; startTime: string; duration: number; location?: Location; diff --git a/packages/playwright/src/reporters/html.ts b/packages/playwright/src/reporters/html.ts index 5aada7e495..09ec7d8471 100644 --- a/packages/playwright/src/reporters/html.ts +++ b/packages/playwright/src/reporters/html.ts @@ -498,7 +498,9 @@ class HtmlBuilder { const { step, duration, count } = dedupedStep; const result: TestStep = { title: step.title, + category: step.category, startTime: step.startTime.toISOString(), + params: step.params, duration, steps: dedupeSteps(step.steps).map(s => this._createTestStep(s)), location: this._relativeLocation(step.location), diff --git a/tests/playwright-test/reporter-html.spec.ts b/tests/playwright-test/reporter-html.spec.ts index 1c5b5bbee4..6148c6bce7 100644 --- a/tests/playwright-test/reporter-html.spec.ts +++ b/tests/playwright-test/reporter-html.spec.ts @@ -876,6 +876,33 @@ for (const useIntermediateMergeReport of [false] as const) { ])); }); + test('should show stwep ID', { annotation: { type: 'issue', description: 'https://github.com/microsoft/playwright/issues/32748' } }, async ({ runInlineTest, page, showReport }) => { + const result = await runInlineTest({ + 'a.test.js': ` + import { test, expect } from '@playwright/test'; + test('passing', async ({ page }, testInfo) => { + testInfo.attachments.push({ + name: 'top-level.txt', + contentType: 'text/plain', + body: Buffer.from('foo'), + }); + await test.step('step', async () => { + testInfo.attachments.push({ + name: 'step-attachment.txt', + contentType: 'text/plain', + body: Buffer.from('foo'), + }); + }); + }); + `, + }, { reporter: 'dot,html' }, { PLAYWRIGHT_HTML_OPEN: 'never' }); + expect(result.exitCode).toBe(0); + + await showReport(); + + await page.pause(); + }); + test('should strikethrough textual diff', async ({ runInlineTest, showReport, page }) => { const result = await runInlineTest({ 'helper.ts': `