From a126f0413e74a0c270ae5ee75bea0364ed245182 Mon Sep 17 00:00:00 2001 From: mrbobbytables Date: Thu, 8 Oct 2026 07:27:45 -0500 Subject: [PATCH] Fold zero regions contradicted by a silent artifact of their own script V8 emits a deviation range only where a count differs from the enclosing one, so an artifact that executes a branch arm uniformly with the code around it records no range over the arm at all. When every truthy-path artifact of a chunk records the arm at zero, that silence leaves the zero standing in the union with no covered twin for the crossing fold (#1163) to catch: useFocusTrap's previousFocus arm (51:25-51:41) runs exactly once this way on the trigger-unmounted page, yet the report counted it uncovered. The silence is proof, but only within one script: one script has one source map, so identical skipped text always lands on the same original span. isContradictedRegion therefore folds a zero region only when some artifact of a script that recorded the zero itself covers all the region's lines while recording no zero touching any of them. Cross-chunk absence proves nothing (drift maps the same dead arm elsewhere), so RadarReports' and DirectoryFreshness's genuinely dead arms survive, as pinned by the regression tests. Measured on a full local run: folds useFocusTrap 51:25-51:41 and profile-links 51:33-51:45 / 53:16-53:28 (members without websites execute those return-null arms in-browser); src regions 438/457 = 95.84%, floor 95 unchanged. The enclosure-pinning fixture now serves its containing covered region from a second chunk: a same-script artifact that is uniform over the arm is V8's statement that the arm executed, which is this fold's evidence. Closes #1202 Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> Signed-off-by: mrbobbytables --- tests/e2e-coverage-report.test.mjs | 232 ++++++++++++++++++++++++---- tests/tools/e2e-coverage-report.mjs | 83 +++++++++- 2 files changed, 281 insertions(+), 34 deletions(-) diff --git a/tests/e2e-coverage-report.test.mjs b/tests/e2e-coverage-report.test.mjs index fc593abe..19ce9e21 100644 --- a/tests/e2e-coverage-report.test.mjs +++ b/tests/e2e-coverage-report.test.mjs @@ -403,56 +403,69 @@ test('a zero-count region spanning only covered lines is not counted against the // for (#1094, #1097). Enclosure is therefore not evidence of drift. // // The two artifacts below put one zero region, `1:6:1:12`, against three -// covered regions that each enclose it in a different way: `1:0:3:12` from the -// *other* artifact (whole-span containment across artifacts), `1:0:1:12` (the -// same line), and `1:6:3:12` (the same start column, differing end -- the -// shape #1066 proposed keying away). It survives all three. +// covered regions that each enclose it in a different way: `1:0:3:12` from a +// *different script* compiled from the same file (whole-span containment +// across chunks -- RadarReports' dead arms are enclosed exactly this way by +// the chunks that never record their zero), `1:0:1:12` (the same line), and +// `1:6:3:12` (the same start column, differing end -- the shape #1066 +// proposed keying away). It survives all three. The enclosing script must be +// a different chunk here: an artifact of the *same* script that covers the +// arm's lines while recording no zero over them is V8's way of saying the arm +// executed, which is the contradiction fold's evidence, pinned separately +// below. test('a single-line zero-count region survives a covered region that encloses it', async () => { const fixture = await fixtureRun(); try { const lines = ['const a = 1;', 'const b = 2;', 'const c = 3;']; const source = `${lines.join('\n')}\n`; - const scriptText = `${source}\n//# sourceMappingURL=app.js.map\n`; const original = join(fixture.root, 'src/components/Example/index.js'); await mkdir(join(fixture.root, 'src/components/Example'), { recursive: true, }); await writeFile(original, source); - await writeFile(join(fixture.buildDir, 'assets/js/app.js'), scriptText); - await writeFile( - join(fixture.buildDir, 'assets/js/app.js.map'), - JSON.stringify({ - version: 3, - file: 'app.js', - sources: ['webpack://endusers/./src/components/Example/index.js'], - sourcesContent: [source], - names: [], - // Line 1 carries a second mapping at column 6 so a block opening and - // closing inside it resolves to columns of its own instead of - // snapping back to the start of the line. Without that the zero - // region would be a zero-width span and prove nothing about columns. - mappings: [ - `${[vlq(0), vlq(0), vlq(0), vlq(0)].join('')},${[ - vlq(6), - vlq(0), - vlq(0), - vlq(6), - ].join('')}`, - `${[vlq(0), vlq(0), vlq(1), vlq(-6)].join('')}`, - `${[vlq(0), vlq(0), vlq(1), vlq(0)].join('')}`, - ].join(';'), - }), - ); + // Two chunks carry the same file, as the real bundle splits do. Line 1 + // carries a second mapping at column 6 so a block opening and closing + // inside it resolves to columns of its own instead of snapping back to + // the start of the line. Without that the zero region would be a + // zero-width span and prove nothing about columns. + const mappings = [ + `${[vlq(0), vlq(0), vlq(0), vlq(0)].join('')},${[ + vlq(6), + vlq(0), + vlq(0), + vlq(6), + ].join('')}`, + `${[vlq(0), vlq(0), vlq(1), vlq(-6)].join('')}`, + `${[vlq(0), vlq(0), vlq(1), vlq(0)].join('')}`, + ].join(';'); + for (const name of ['app.js', 'app2.js']) { + await writeFile( + join(fixture.buildDir, `assets/js/${name}`), + `${source}\n//# sourceMappingURL=${name}.map\n`, + ); + await writeFile( + join(fixture.buildDir, `assets/js/${name}.map`), + JSON.stringify({ + version: 3, + file: name, + sources: ['webpack://endusers/./src/components/Example/index.js'], + sourcesContent: [source], + names: [], + mappings, + }), + ); + } + const scriptText = `${source}\n//# sourceMappingURL=app.js.map\n`; - // One page runs the whole script and nothing else, contributing a covered - // region that spans every line of the file. + // One page runs the whole of the *other* chunk and nothing else, + // contributing a covered region that spans every line of the file. await writeCoverageArtifact(fixture.runDir, 'worker-0-page-0', { schemaVersion: 1, kind: 'endusers.playwright.v8-coverage', runId: 'run-1', result: [ { - url: 'http://localhost:3000/assets/js/app.js', + url: 'http://localhost:3000/assets/js/app2.js', scriptId: '1', functions: [ { @@ -632,6 +645,159 @@ test('a zero-count region crossed by a covered one is treated as source-map drif } }); +// Drift needs the twin *recorded*; one shape leaves none (#1202). V8 emits a +// deviation range only where a count differs from the enclosing one, so an +// artifact that executes a branch arm at the same count as the code around it +// carries no range over the arm at all -- `useFocusTrap`'s `previousFocus` +// arm runs exactly like that on the trigger-unmounted page, while every +// truthy-path artifact of the same chunk records `51:25-51:41` at zero. The +// zero then survives the union with no covered region sharing or crossing its +// key. The silence is still proof, but only within one script: one script has +// one source map, so had the arm been skipped in the silent artifact too, the +// identical zero mapping would have reappeared. These three tests pin the +// fold and both edges of its evidence requirement. +// +// Shared fixture shape: one source file carried by one chunk, line 1 mapped +// at columns 0, 3 and 6 so distinct spans inside it resolve to distinct +// original columns. Artifacts differ only in their V8 ranges. +async function contradictionFixture(buildArtifacts) { + const fixture = await fixtureRun(); + const lines = ['const a = 1;', 'const b = 2;', 'const c = 3;']; + const source = `${lines.join('\n')}\n`; + const scriptText = `${source}\n//# sourceMappingURL=app.js.map\n`; + await mkdir(join(fixture.root, 'src/components/Example'), { + recursive: true, + }); + await writeFile( + join(fixture.root, 'src/components/Example/index.js'), + source, + ); + await writeFile(join(fixture.buildDir, 'assets/js/app.js'), scriptText); + await writeFile( + join(fixture.buildDir, 'assets/js/app.js.map'), + JSON.stringify({ + version: 3, + file: 'app.js', + sources: ['webpack://endusers/./src/components/Example/index.js'], + sourcesContent: [source], + names: [], + mappings: [ + [ + [vlq(0), vlq(0), vlq(0), vlq(0)].join(''), + [vlq(3), vlq(0), vlq(0), vlq(3)].join(''), + [vlq(3), vlq(0), vlq(0), vlq(3)].join(''), + ].join(','), + [vlq(0), vlq(0), vlq(1), vlq(-6)].join(''), + [vlq(0), vlq(0), vlq(1), vlq(0)].join(''), + ].join(';'), + }), + ); + const artifacts = buildArtifacts(scriptText.length); + for (const [index, { url, ranges }] of artifacts.entries()) { + await writeCoverageArtifact(fixture.runDir, `worker-0-page-${index}`, { + schemaVersion: 1, + kind: 'endusers.playwright.v8-coverage', + runId: 'run-1', + result: [ + { + url: url ?? 'http://localhost:3000/assets/js/app.js', + scriptId: String(index + 1), + functions: [{ functionName: '', isBlockCoverage: true, ranges }], + }, + ], + }); + } + await sealCoverageRun(fixture.runDir, 'passed'); + return fixture; +} + +test('a zero-count region contradicted by a silent artifact of its own script is folded', async () => { + // Page 0 skips the arm at columns 6-10 and records the zero; page 1 runs + // the whole script uniformly, so V8 emits no range over the arm at all. + // Same script, lines covered, no zero anywhere near it: the arm executed. + const fixture = await contradictionFixture((length) => [ + { + ranges: [ + { startOffset: 0, endOffset: length, count: 1 }, + { startOffset: 6, endOffset: 10, count: 0 }, + ], + }, + { ranges: [{ startOffset: 0, endOffset: length, count: 1 }] }, + ]); + try { + const report = await collectE2ECoverage(fixture.runDir, { + root: fixture.root, + buildDir: fixture.buildDir, + }); + assert.equal(report.status, 'ok'); + const [entry] = report.sources; + assert.equal(entry.file, 'src/components/Example/index.js'); + assert.deepEqual(entry.uncoveredRegions, []); + assert.equal(entry.regions, entry.coveredRegions); + } finally { + await rm(fixture.root, { recursive: true, force: true }); + } +}); + +test('a zero-count region recorded by every artifact of its script survives', async () => { + // Both pages skip the arm -- the genuinely dead shape (RadarReports' + // empty-corpus arms). No artifact of the chunk is silent about it, so + // nothing contradicts the zero. + const skipArm = (length) => [ + { startOffset: 0, endOffset: length, count: 1 }, + { startOffset: 6, endOffset: 10, count: 0 }, + ]; + const fixture = await contradictionFixture((length) => [ + { ranges: skipArm(length) }, + { ranges: skipArm(length) }, + ]); + try { + const report = await collectE2ECoverage(fixture.runDir, { + root: fixture.root, + buildDir: fixture.buildDir, + }); + assert.equal(report.status, 'ok'); + const [entry] = report.sources; + assert.deepEqual(entry.uncoveredRegions, [1]); + assert.equal(entry.regions - entry.coveredRegions, 1); + } finally { + await rm(fixture.root, { recursive: true, force: true }); + } +}); + +test('a witness with any zero touching the region lines does not contradict it', async () => { + // Page 1 covers the arm's line but skips the *neighbouring* arm at columns + // 3-6 on the same line. A zero that near the region means the witness was + // on a path where flattening could have merged or shifted spans, so it is + // disqualified -- both zeros survive, neither contradicts the other. + const fixture = await contradictionFixture((length) => [ + { + ranges: [ + { startOffset: 0, endOffset: length, count: 1 }, + { startOffset: 6, endOffset: 10, count: 0 }, + ], + }, + { + ranges: [ + { startOffset: 0, endOffset: length, count: 1 }, + { startOffset: 3, endOffset: 6, count: 0 }, + ], + }, + ]); + try { + const report = await collectE2ECoverage(fixture.runDir, { + root: fixture.root, + buildDir: fixture.buildDir, + }); + assert.equal(report.status, 'ok'); + const [entry] = report.sources; + assert.deepEqual(entry.uncoveredRegions, [1]); + assert.equal(entry.regions - entry.coveredRegions, 2); + } finally { + await rm(fixture.root, { recursive: true, force: true }); + } +}); + // `npm run build:e2e:coverage` compiles the site twice: once from the real // data, and once with tests/e2e/fixtures/data-variants/** layered on, into // build/e2e-coverage-variant under its own base URL. That is what makes a diff --git a/tests/tools/e2e-coverage-report.mjs b/tests/tools/e2e-coverage-report.mjs index b09314ff..ce643b28 100644 --- a/tests/tools/e2e-coverage-report.mjs +++ b/tests/tools/e2e-coverage-report.mjs @@ -391,6 +391,71 @@ function isDriftedRegion(region, regions) { return false; } +// The crossing fold above needs the drifted twin to be *recorded*. One shape +// leaves no twin at all (#1202): when an artifact executes a span at the same +// count as its enclosing code, V8 emits no deviation range over it, so the +// artifact carries no region -- covered or zero -- for the span. +// `useFocusTrap`'s cleanup runs once with the trigger unmounted and the +// `previousFocus` arm executes uniformly with the arrow around it; that +// artifact records lines 49-51 covered and no range in the cleanup at all, +// while every truthy-path artifact of the same chunk records `51:25-51:41` +// at zero. The zero survives the union because no covered region ever shares +// (or crosses) its key. +// +// Absence only proves execution inside one script: V8 emits a zero range +// wherever text inside executed code did not run, and one script has one +// source map, so the same unexecuted text always lands on the same original +// span. If some artifact of a script records a zero region and another +// artifact of the *same script* covers the region's lines while recording no +// zero on any of them, the second artifact executed that text -- had it been +// skipped there too, the identical zero mapping would reappear. Across +// scripts the inference fails: a different bundle maps the same skipped arm +// to a different original span (#1066's drift), so a chunk that never +// records the zero at these coordinates says nothing about them. The witness +// is therefore required to come from a script that produced the zero itself. +// The exclusion test is by line rather than exact span, the conservative +// direction: a zero whose flattened range grew past the arm (adjacent +// unexecuted text merges into one range) still disqualifies the witness. +function zeroTouchesLines(zero, region) { + return zero.line <= region.endLine && zero.endLine >= region.line; +} + +function regionKey(region) { + return [region.line, region.column, region.endLine, region.endColumn].join( + ':', + ); +} + +function isContradictedRegion(region, witnesses) { + if (region.count > 0) return false; + const key = regionKey(region); + const scripts = new Set(); + for (const witness of witnesses) { + if (witness.zeroKeys.has(key)) scripts.add(witness.script); + } + if (scripts.size === 0) return false; + for (const witness of witnesses) { + if (!scripts.has(witness.script)) continue; + let sawExecutableLine = false; + let linesCovered = true; + for (let line = region.line; line <= region.endLine; line += 1) { + const count = witness.lines.get(line); + // Blank lines and comments carry no statement; they neither confirm + // nor contradict, exactly as in isPhantomRegion. + if (count === undefined) continue; + sawExecutableLine = true; + if (count <= 0) { + linesCovered = false; + break; + } + } + if (!sawExecutableLine || !linesCovered) continue; + if (witness.zeros.some((zero) => zeroTouchesLines(zero, region))) continue; + return true; + } + return false; +} + // A region is one branch location from the istanbul object convertScript // already builds -- the arm of a ternary, a short-circuit operand, a default // parameter -- data the line map cannot see because several of them share a @@ -600,6 +665,7 @@ export async function collectE2ECoverage( const target = sources.get(relativePath) ?? { lines: new Map(), regions: new Map(), + witnesses: [], }; for (const [line, count] of lineCoverage) { target.lines.set(line, Math.max(target.lines.get(line) ?? 0, count)); @@ -613,6 +679,20 @@ export async function collectE2ECoverage( target.regions.set(key, region); } } + // Each conversion is one artifact's view of one script: a complete + // partition of that text into executed and zero spans. Kept whole, + // with the script's identity, so isContradictedRegion can ask whether + // an artifact of the same script executed a region's lines without + // recording any zero on them. + const zeros = [...regionCoverage.values()].filter( + (region) => region.count <= 0, + ); + target.witnesses.push({ + script: scriptCoverage.url, + lines: lineCoverage, + zeros, + zeroKeys: new Set(zeros.map(regionKey)), + }); sources.set(relativePath, target); unmapped.delete(relativePath); } @@ -633,7 +713,8 @@ export async function collectE2ECoverage( const regionValues = allRegions.filter( (region) => !isPhantomRegion(region, coverage.lines) && - !isDriftedRegion(region, allRegions), + !isDriftedRegion(region, allRegions) && + !isContradictedRegion(region, coverage.witnesses), ); const regions = regionValues.length; const coveredRegions = regionValues.filter(