fix: restore E2E coverage source mapping - #14950
Conversation
`build.sourcemap: 'hidden'` (#14209) stopped emitting the `//# sourceMappingURL=` comment into the bundles. monocart discovers source maps only through that comment, so every E2E V8 coverage entry stayed at its served bundle path (`localhost-8188/assets/*.js`) instead of mapping back to `src/**`. The coverage merge job then stripped all of them and either failed outright (no `e2e-coverage` artifact, so the Slack report dropped its E2E line) or was left with a lone third-party script — `js.stripe.com/dahlia/stripe.js`, fully covered — and reported E2E coverage as 100%. - Re-inject the comment for the CI E2E build only, via EXPOSE_SOURCEMAP_URL. Shipped builds keep 'hidden', so the .js.map 404 noise FE-1405 fixed stays gone. - Fail the merge job loudly when the tracefile has no source-mapped files, instead of surfacing it as an opaque `lcov: no valid records found`. - Count only `src/`/`packages/` files in the Slack report and treat an implausibly small file set as no data, so a degenerate tracefile can't be announced as a coverage milestone.
🎭 Playwright: ✅ 1792 passed, 0 failed · 2 flaky📊 Browser Reports
📦 Bundle: 8.69 MB gzip ⚪ 0 BDetailsSummary
Category Glance App Entry Points — 3.67 kB (baseline 3.67 kB) • ⚪ 0 BMain entry bundles and manifests Status: 1 unchanged Graph Workspace — 1.36 MB (baseline 1.36 MB) • ⚪ 0 BGraph editor runtime, canvas, workflow orchestration Status: 3 unchanged Views & Navigation — 124 kB (baseline 124 kB) • ⚪ 0 BTop-level views, pages, and routed surfaces Status: 17 unchanged Panels & Settings — 570 kB (baseline 570 kB) • ⚪ 0 BConfiguration panels, inspectors, and settings screens Status: 26 unchanged User & Accounts — 27 kB (baseline 27 kB) • ⚪ 0 BAuthentication, profile, and account management bundles Status: 10 unchanged Editors & Dialogs — 125 kB (baseline 125 kB) • ⚪ 0 BModals, dialogs, drawers, and in-app editors Status: 8 unchanged UI Components — 67.1 kB (baseline 67.1 kB) • ⚪ 0 BReusable component library chunks Status: 14 unchanged Data & Services — 3.5 MB (baseline 3.5 MB) • ⚪ 0 BStores, services, APIs, and repositories Status: 17 unchanged Utilities & Hooks — 550 kB (baseline 550 kB) • ⚪ 0 BHelpers, composables, and utility bundles Status: 38 unchanged Vendor & Third-Party — 16.3 MB (baseline 16.3 MB) • ⚪ 0 BExternal libraries and shared vendor chunks Status: 17 unchanged Other — 14 MB (baseline 14 MB) • ⚪ 0 BBundles that do not match a named category Status: 286 unchanged ⚡ Performance Report
Show regressions
All metrics
Historical variance (last 15 runs)
Trend (last 15 commits on main)
Raw data{
"timestamp": "2026-08-09T03:22:05.609Z",
"gitSha": "d57a44c3d399dacf5932928f834abb607bd4ffbf",
"branch": "fix/e2e-coverage-sourcemap-url",
"measurements": [
{
"name": "canvas-idle",
"durationMs": 2166.086000000007,
"styleRecalcs": 7,
"styleRecalcDurationMs": 7.865,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 573.4110000000001,
"heapDeltaBytes": 5805872,
"heapUsedBytes": 70140088,
"domNodes": 14,
"jsHeapTotalBytes": 24117248,
"scriptDurationMs": 22.935000000000002,
"eventListeners": 6,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.666666666666668,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "canvas-idle",
"durationMs": 2021.8869999999924,
"styleRecalcs": 11,
"styleRecalcDurationMs": 9.154999999999998,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 472.40399999999994,
"heapDeltaBytes": 5776204,
"heapUsedBytes": 69930344,
"domNodes": 22,
"jsHeapTotalBytes": 24117248,
"scriptDurationMs": 16.545,
"eventListeners": 4,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.670000000000012,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "canvas-mouse-sweep",
"durationMs": 1857.0519999999817,
"styleRecalcs": 74,
"styleRecalcDurationMs": 39.273999999999994,
"layouts": 12,
"layoutDurationMs": 3.6659999999999995,
"taskDurationMs": 938.3960000000001,
"heapDeltaBytes": -14071256,
"heapUsedBytes": 50196696,
"domNodes": -282,
"jsHeapTotalBytes": 23568384,
"scriptDurationMs": 128.518,
"eventListeners": -153,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.666666666666668,
"p95FrameDurationMs": 16.800000000000182
},
{
"name": "canvas-mouse-sweep",
"durationMs": 1861.7569999999546,
"styleRecalcs": 76,
"styleRecalcDurationMs": 38.981,
"layouts": 12,
"layoutDurationMs": 3.68,
"taskDurationMs": 850.125,
"heapDeltaBytes": 207936,
"heapUsedBytes": 64568108,
"domNodes": 61,
"jsHeapTotalBytes": 24641536,
"scriptDurationMs": 122.24399999999999,
"eventListeners": 4,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.66333333333332,
"p95FrameDurationMs": 16.800000000000182
},
{
"name": "canvas-zoom-sweep",
"durationMs": 1722.426999999982,
"styleRecalcs": 32,
"styleRecalcDurationMs": 18.662,
"layouts": 6,
"layoutDurationMs": 0.7049999999999998,
"taskDurationMs": 398.265,
"heapDeltaBytes": 8730628,
"heapUsedBytes": 72899808,
"domNodes": 78,
"jsHeapTotalBytes": 24641536,
"scriptDurationMs": 22.215000000000003,
"eventListeners": 19,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.666666666666668,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "canvas-zoom-sweep",
"durationMs": 1672.9860000000372,
"styleRecalcs": 31,
"styleRecalcDurationMs": 14.377999999999998,
"layouts": 6,
"layoutDurationMs": 0.505,
"taskDurationMs": 369.139,
"heapDeltaBytes": 8512220,
"heapUsedBytes": 72840068,
"domNodes": 77,
"jsHeapTotalBytes": 24379392,
"scriptDurationMs": 17.657,
"eventListeners": 19,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.666666666666668,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "dom-widget-clipping",
"durationMs": 585.8929999999987,
"styleRecalcs": 11,
"styleRecalcDurationMs": 7.777999999999999,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 386.856,
"heapDeltaBytes": -11314708,
"heapUsedBytes": 53242776,
"domNodes": 18,
"jsHeapTotalBytes": 24903680,
"scriptDurationMs": 60.852999999999994,
"eventListeners": 0,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.66333333333332,
"p95FrameDurationMs": 16.799999999999272
},
{
"name": "dom-widget-clipping",
"durationMs": 598.3870000000024,
"styleRecalcs": 13,
"styleRecalcDurationMs": 9.279,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 383.09200000000004,
"heapDeltaBytes": -11258004,
"heapUsedBytes": 53265208,
"domNodes": 22,
"jsHeapTotalBytes": 25690112,
"scriptDurationMs": 57.693,
"eventListeners": 2,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.666666666666668,
"p95FrameDurationMs": 16.800000000000182
},
{
"name": "large-graph-idle",
"durationMs": 2040.255000000002,
"styleRecalcs": 9,
"styleRecalcDurationMs": 9.106,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 748.0250000000002,
"heapDeltaBytes": 6995696,
"heapUsedBytes": 66382204,
"domNodes": -282,
"jsHeapTotalBytes": 3248128,
"scriptDurationMs": 122.915,
"eventListeners": -149,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.66333333333332,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "large-graph-idle",
"durationMs": 2011.0899999999674,
"styleRecalcs": 8,
"styleRecalcDurationMs": 8.140999999999998,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 670.423,
"heapDeltaBytes": 4383496,
"heapUsedBytes": 63886468,
"domNodes": -281,
"jsHeapTotalBytes": 3510272,
"scriptDurationMs": 101.26899999999999,
"eventListeners": -179,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.66333333333332,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "large-graph-pan",
"durationMs": 2251.4340000000175,
"styleRecalcs": 69,
"styleRecalcDurationMs": 14.393000000000002,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 1346.349,
"heapDeltaBytes": 3774372,
"heapUsedBytes": 64383580,
"domNodes": -287,
"jsHeapTotalBytes": 3964928,
"scriptDurationMs": 445.08500000000004,
"eventListeners": -149,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.666666666666668,
"p95FrameDurationMs": 16.800000000000182
},
{
"name": "large-graph-pan",
"durationMs": 2220.2000000000908,
"styleRecalcs": 68,
"styleRecalcDurationMs": 12.797000000000002,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 1284.014,
"heapDeltaBytes": 20158620,
"heapUsedBytes": 80647328,
"domNodes": -284,
"jsHeapTotalBytes": 4227072,
"scriptDurationMs": 423.723,
"eventListeners": -179,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.666666666666668,
"p95FrameDurationMs": 16.699999999999818
},
{
"name": "large-graph-zoom",
"durationMs": 3260.356999999999,
"styleRecalcs": 64,
"styleRecalcDurationMs": 14.356999999999998,
"layouts": 60,
"layoutDurationMs": 7.4879999999999995,
"taskDurationMs": 1530.817,
"heapDeltaBytes": 24074720,
"heapUsedBytes": 86867388,
"domNodes": 10,
"jsHeapTotalBytes": 7602176,
"scriptDurationMs": 544.081,
"eventListeners": 8,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.66333333333335,
"p95FrameDurationMs": 16.799999999999272
},
{
"name": "large-graph-zoom",
"durationMs": 3198.154999999929,
"styleRecalcs": 66,
"styleRecalcDurationMs": 15.340999999999998,
"layouts": 60,
"layoutDurationMs": 7.273,
"taskDurationMs": 1490.413,
"heapDeltaBytes": -1831400,
"heapUsedBytes": 60092356,
"domNodes": -287,
"jsHeapTotalBytes": 6918144,
"scriptDurationMs": 524.047,
"eventListeners": -153,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.666666666666668,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "minimap-idle",
"durationMs": 2036.8030000000203,
"styleRecalcs": 8,
"styleRecalcDurationMs": 7.907000000000001,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 710.587,
"heapDeltaBytes": 6608552,
"heapUsedBytes": 67263764,
"domNodes": -283,
"jsHeapTotalBytes": 4296704,
"scriptDurationMs": 117.43800000000002,
"eventListeners": -179,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.66333333333335,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "minimap-idle",
"durationMs": 2033.9999999999918,
"styleRecalcs": 7,
"styleRecalcDurationMs": 6.463,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 666.5660000000001,
"heapDeltaBytes": 6704924,
"heapUsedBytes": 67214704,
"domNodes": -285,
"jsHeapTotalBytes": 3510272,
"scriptDurationMs": 103.848,
"eventListeners": -149,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.66333333333335,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "subgraph-dom-widget-clipping",
"durationMs": 611.1569999999915,
"styleRecalcs": 47,
"styleRecalcDurationMs": 10.797999999999998,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 415.1,
"heapDeltaBytes": -11175100,
"heapUsedBytes": 53437816,
"domNodes": 20,
"jsHeapTotalBytes": 25690112,
"scriptDurationMs": 121.677,
"eventListeners": 6,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.666666666666668,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "subgraph-dom-widget-clipping",
"durationMs": 561.3999999999351,
"styleRecalcs": 48,
"styleRecalcDurationMs": 10.944999999999999,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 388.99300000000005,
"heapDeltaBytes": -10521164,
"heapUsedBytes": 53767020,
"domNodes": 22,
"jsHeapTotalBytes": 25952256,
"scriptDurationMs": 115.321,
"eventListeners": 6,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.666666666666668,
"p95FrameDurationMs": 16.800000000000182
},
{
"name": "subgraph-idle",
"durationMs": 2014.9429999999597,
"styleRecalcs": 10,
"styleRecalcDurationMs": 9.520999999999999,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 529.202,
"heapDeltaBytes": 5988540,
"heapUsedBytes": 70352920,
"domNodes": 20,
"jsHeapTotalBytes": 24903680,
"scriptDurationMs": 20.054000000000002,
"eventListeners": 4,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.666666666666668,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "subgraph-idle",
"durationMs": 2005.5699999999206,
"styleRecalcs": 9,
"styleRecalcDurationMs": 7.710000000000002,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 445.6809999999999,
"heapDeltaBytes": 5948072,
"heapUsedBytes": 70481784,
"domNodes": 18,
"jsHeapTotalBytes": 24641536,
"scriptDurationMs": 13.745999999999999,
"eventListeners": 4,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.66333333333335,
"p95FrameDurationMs": 16.699999999999818
},
{
"name": "subgraph-mouse-sweep",
"durationMs": 1739.7740000000113,
"styleRecalcs": 77,
"styleRecalcDurationMs": 38.45,
"layouts": 16,
"layoutDurationMs": 4.3759999999999994,
"taskDurationMs": 855.5579999999999,
"heapDeltaBytes": -15766260,
"heapUsedBytes": 48686420,
"domNodes": -279,
"jsHeapTotalBytes": 23044096,
"scriptDurationMs": 97.95,
"eventListeners": -153,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.666666666666668,
"p95FrameDurationMs": 16.800000000000182
},
{
"name": "subgraph-mouse-sweep",
"durationMs": 1741.2760000000844,
"styleRecalcs": 77,
"styleRecalcDurationMs": 36.836999999999996,
"layouts": 16,
"layoutDurationMs": 4.799,
"taskDurationMs": 837.106,
"heapDeltaBytes": -16335816,
"heapUsedBytes": 48026948,
"domNodes": -279,
"jsHeapTotalBytes": 22257664,
"scriptDurationMs": 93.845,
"eventListeners": -153,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.666666666666668,
"p95FrameDurationMs": 16.699999999999818
},
{
"name": "subgraph-transition-enter",
"durationMs": 1384.4879999999762,
"styleRecalcs": 17,
"styleRecalcDurationMs": 29.74700000000001,
"layouts": 13,
"layoutDurationMs": 12.021,
"taskDurationMs": 924.946,
"heapDeltaBytes": 30978888,
"heapUsedBytes": 99448836,
"domNodes": 13673,
"jsHeapTotalBytes": 15466496,
"scriptDurationMs": 33.43300000000001,
"eventListeners": 2375,
"totalBlockingTimeMs": 134,
"frameDurationMs": 16.66333333333332,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "viewport-pan-sweep",
"durationMs": 8468.38200000002,
"styleRecalcs": 250,
"styleRecalcDurationMs": 37.43,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 4727.288,
"heapDeltaBytes": 12767044,
"heapUsedBytes": 72139512,
"domNodes": -281,
"jsHeapTotalBytes": 5799936,
"scriptDurationMs": 1432.485,
"eventListeners": -131,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.669999999999952,
"p95FrameDurationMs": 16.799999999999272
},
{
"name": "viewport-pan-sweep",
"durationMs": 8352.827000000048,
"styleRecalcs": 250,
"styleRecalcDurationMs": 36.472,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 4476.744,
"heapDeltaBytes": 5448180,
"heapUsedBytes": 64897992,
"domNodes": -281,
"jsHeapTotalBytes": 5537792,
"scriptDurationMs": 1362.6970000000001,
"eventListeners": -163,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.666666666666668,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "vue-large-graph-idle",
"durationMs": 12934.976000000006,
"styleRecalcs": 0,
"styleRecalcDurationMs": 0,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 12908.083999999999,
"heapDeltaBytes": -54424904,
"heapUsedBytes": 171747484,
"domNodes": -8312,
"jsHeapTotalBytes": -1777664,
"scriptDurationMs": 594.5879999999999,
"eventListeners": -16389,
"totalBlockingTimeMs": 0,
"frameDurationMs": 17.776666666666642,
"p95FrameDurationMs": 16.799999999999272
},
{
"name": "vue-large-graph-idle",
"durationMs": 17137.778999999908,
"styleRecalcs": 0,
"styleRecalcDurationMs": 0,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 17110.577999999998,
"heapDeltaBytes": -61965196,
"heapUsedBytes": 167151412,
"domNodes": -8312,
"jsHeapTotalBytes": -6496256,
"scriptDurationMs": 608.1419999999999,
"eventListeners": -16387,
"totalBlockingTimeMs": 0,
"frameDurationMs": 17.776666666666642,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "vue-large-graph-pan",
"durationMs": 20889.051999999992,
"styleRecalcs": 143,
"styleRecalcDurationMs": 17.940000000000012,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 20841.672,
"heapDeltaBytes": -44214384,
"heapUsedBytes": 178711604,
"domNodes": -8312,
"jsHeapTotalBytes": -8663040,
"scriptDurationMs": 953.9629999999999,
"eventListeners": -16383,
"totalBlockingTimeMs": 215,
"frameDurationMs": 17.77333333333336,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "vue-large-graph-pan",
"durationMs": 21002.357000000076,
"styleRecalcs": 144,
"styleRecalcDurationMs": 19.028000000000045,
"layouts": 0,
"layoutDurationMs": 0,
"taskDurationMs": 20938.307,
"heapDeltaBytes": -66268292,
"heapUsedBytes": 156071948,
"domNodes": -8312,
"jsHeapTotalBytes": -10948608,
"scriptDurationMs": 928.379,
"eventListeners": -16383,
"totalBlockingTimeMs": 265,
"frameDurationMs": 17.780000000000047,
"p95FrameDurationMs": 16.799999999999272
},
{
"name": "workflow-execution",
"durationMs": 117.8780000000188,
"styleRecalcs": 9,
"styleRecalcDurationMs": 17.444000000000003,
"layouts": 3,
"layoutDurationMs": 1.1630000000000003,
"taskDurationMs": 91.41899999999998,
"heapDeltaBytes": 3197352,
"heapUsedBytes": 66465168,
"domNodes": 114,
"jsHeapTotalBytes": 3145728,
"scriptDurationMs": 9.392000000000001,
"eventListeners": 49,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.666666666666668,
"p95FrameDurationMs": 16.700000000000728
},
{
"name": "workflow-execution",
"durationMs": 463.1920000000491,
"styleRecalcs": 14,
"styleRecalcDurationMs": 20.759,
"layouts": 3,
"layoutDurationMs": 0.6900000000000001,
"taskDurationMs": 112.94999999999999,
"heapDeltaBytes": 5057512,
"heapUsedBytes": 68457152,
"domNodes": 123,
"jsHeapTotalBytes": 5505024,
"scriptDurationMs": 10.148000000000001,
"eventListeners": 97,
"totalBlockingTimeMs": 0,
"frameDurationMs": 16.670000000000012,
"p95FrameDurationMs": 16.800000000000182
}
]
} |
|
Warning Review limit reachedYou’ve reached a temporary PR review limit under our Fair Usage Limits Policy. Next review available in: 34 minutes Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available. How can I continue?After more reviews become available, a review can be triggered using the To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews. How do review limits work?CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability. For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window. Please refer docs for additional details. Review details⚙️ Run configurationConfiguration used: Path: .coderabbit.yaml Review profile: ASSERTIVE Plan: Pro Plus Run ID: 📒 Files selected for processing (5)
📝 WalkthroughWalkthroughThe change enables source-map coverage in E2E builds, filters LCOV data to project files, requires at least 100 source files, and validates this threshold in the E2E coverage workflow. ChangesCoverage source maps
Estimated code review effort: 3 (Moderate) | ~20 minutes Sequence Diagram(s)sequenceDiagram
participant E2ESetup as E2E setup job
participant Vite as vite.config.mts
participant LCOV as LCOV parser
participant Workflow as E2E coverage workflow
E2ESetup->>Vite: Enable COLLECT_COVERAGE
Vite->>LCOV: Produce source-mapped coverage data
LCOV->>Workflow: Filter and count src/ and packages/ entries
Workflow-->>Workflow: Fail when fewer than 100 files are found
Suggested reviewers: Important Pre-merge checks failedPlease resolve all errors before merging. Addressing warnings is optional. ❌ Failed checks (1 inconclusive)
✅ Passed checks (5 passed)
✨ Finishing Touches 💡 1🛠️ Fix failing CI checks 💡
📝 Generate docstrings
🧪 Generate unit tests (beta)
Comment |
There was a problem hiding this comment.
Actionable comments posted: 1
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@scripts/coverage-slack-notify.test.ts`:
- Around line 49-54: Add a behavioral assertion in the “too few project files”
test around parseLcovContent and sourceEntries that covers exactly 100 project
files, verifying the documented minimum-boundary behavior while preserving the
existing below-threshold assertion for 99 files and the unrelated single-file
case.
🪄 Autofix
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: ASSERTIVE
Plan: Pro Plus
Run ID: b41b06af-d9c4-4e16-9ff4-5b5de5ca05d1
📒 Files selected for processing (6)
.github/actions/setup-frontend/action.yaml.github/workflows/ci-tests-e2e-coverage.yaml.github/workflows/ci-tests-e2e.yamlscripts/coverage-slack-notify.test.tsscripts/coverage-slack-notify.tsvite.config.mts
Reuses the flag that already marks an E2E coverage run instead of adding a second sourcemap knob, dropping the setup-frontend input along with it. GENERATE_SOURCEMAP can't carry this: Comfy-Org/cloud already sets it true for the staging and prod builds, which must keep 'hidden'.
There was a problem hiding this comment.
Actionable comments posted: 2
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In @.github/workflows/ci-tests-e2e-coverage.yaml:
- Around line 94-95: Update the coverage validation around MAPPED_SF to report
the observed SF path format from the merged tracefile instead of attributing
every failure to missing source maps. Preserve the failure for insufficient
mapped project files, while including representative SF paths and distinguishing
absolute paths, file:// URLs, and low mapped-file counts in the error output.
In @.github/workflows/ci-tests-e2e.yaml:
- Around line 32-35: Scope COLLECT_COVERAGE=true to the E2E frontend build by
moving it from the job-level env block to the Setup frontend step, or explicitly
unset it for Build cloud frontend. Ensure pnpm build:cloud runs without
coverage-enabled sourcemaps while the frontend build used for V8 coverage
retains the variable.
🪄 Autofix
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: ASSERTIVE
Plan: Pro Plus
Run ID: 5e22aaa0-6db5-441e-9cc7-975fdeba8b76
📒 Files selected for processing (3)
.github/workflows/ci-tests-e2e-coverage.yaml.github/workflows/ci-tests-e2e.yamlvite.config.mts
Codecov Report✅ All modified and coverable lines are covered by tests. @@ Coverage Diff @@
## main #14950 +/- ##
========================================
Coverage 78.75% 78.76%
========================================
Files 1868 1868
Lines 115515 115821 +306
Branches 33610 33734 +124
========================================
+ Hits 90979 91228 +249
- Misses 23992 24036 +44
- Partials 544 557 +13
Flags with carried forward coverage won't be shown. Click here to find out more. 🚀 New features to boost your workflow:
|
Addresses review feedback: - Job-level env also reached `Build cloud frontend`, putting sourcemap comments in the cloud artifact. Scope it to the `Setup frontend` step. - Report the SF paths actually observed rather than naming one cause. - Cover the exact MIN_SOURCE_FILES boundary.
| sourcemap: GENERATE_SOURCEMAP | ||
| ? COLLECT_COVERAGE | ||
| ? true | ||
| : 'hidden' | ||
| : false, |
There was a problem hiding this comment.
Ternary is a little awkward.
The boolean form is also a little awkward:
sourcemap: !!GENERATE_SOURCEMAP && (!!COLLECT_COVERAGE || 'hidden'),There was a problem hiding this comment.
Dropped the nesting — GENERATE_SOURCEMAP && (COLLECT_COVERAGE || 'hidden'), without the !! since both are already booleans. 78c9f9a
| # The build must emit `//# sourceMappingURL=` comments or monocart cannot | ||
| # map the sharded job's V8 coverage back to src/**. See vite.config.mts. |
There was a problem hiding this comment.
| # The build must emit `//# sourceMappingURL=` comments or monocart cannot | |
| # map the sharded job's V8 coverage back to src/**. See vite.config.mts. |
There was a problem hiding this comment.
Removed; vite.config.mts still explains the coupling. 78c9f9a
.pinact.yaml allowlists actions/download-artifact at v8, so this one straggler fails validate-pins on every PR that touches this file. The other five uses in the same workflow are already v8.
3e5bc25
Per review: drop the nested ternary and the workflow comment. vite.config.mts still carries the explanation.
<!-- ccr-slack-attribution --> _Requested by **Christian Byrne** · [Slack thread](https://comfy-organization.slack.com/archives/C0AP09LKRDZ/p1786872633268499?thread_ts=1786872633.268499&cid=C0AP09LKRDZ)_ ## Summary The e2e coverage merge job only ran when the upstream `CI: Tests E2E` workflow's overall conclusion was `success`, so a single flaky shard (16-shard matrix, `fail-fast: false`) skipped merging every other shard's real coverage — the reported % bounces around a narrow band instead of climbing as coverage improves. ## Changes - **What**: `merge` job in `.github/workflows/ci-tests-e2e-coverage.yaml` now runs on any completed conclusion except `cancelled` (was: `== 'success'`), so partial-shard-failure runs still get merged. One-line comment added explaining why. - **Breaking**: none ## Review Focus - The download-artifact step already tolerates a partial set of shard artifacts (regex-matched artifact names + `if_no_artifact_found: warn`), and each shard's coverage-upload step runs with `if: always()`, so it already didn't assume all 16 shards would be present — no change needed there. - The "Assert coverage was mapped back to source" step (minimum source-mapped file count, added in Comfy-Org#14950) is untouched — still fails the job loudly on a degenerate merge. - `coverage-slack-notify.yaml` already downloads the `e2e-coverage` artifact with `continue-on-error: true` / `if_no_artifact_found: warn`, and `scripts/coverage-slack-notify.ts` already treats a missing/degenerate lcov as "no data" rather than an anomaly — no change needed there either. - No new jobs, retries, or timeouts added, so this doesn't add CI wall-clock time — it's purely a gating/condition change on an existing job. --- _Generated by [Claude Code](https://claude.ai/code/session_01CdcyUD4e6kt6CAuRNkEJ7H)_ Co-authored-by: Claude <noreply@anthropic.com>
Summary
E2E coverage has been reported as either missing or 100% since
build.sourcemap: 'hidden'landed; this restores the source mapping and adds guards so a degenerate tracefile fails loudly instead of being announced as a milestone.Changes
COLLECT_COVERAGE=true, which re-injects the//# sourceMappingURL=comment. Everything that ships to users keeps'hidden', so the.js.map404 noise FE-1405 removed stays gone.GENERATE_SOURCEMAPcan't carry this —Comfy-Org/cloudalready sets it true for the staging and prod builds.CI: E2E Coverageasserts the merged tracefile still has source-mapped files before stripping bundle paths, with an error that names the cause.coverage-slack-notify.tscounts onlysrc//packages/files and treats an implausibly small file set as no data.Review Focus
Root cause: monocart-coverage-reports resolves source maps only from the
//# sourceMappingURL=comment in the served bundle (lib/converter/collect-source-maps.js). #14209 switchedbuild.sourcemapto'hidden', which emits the.mapfiles but strips that comment, so every V8 coverage entry stayed at its served path (localhost-8188/assets/*.js).The merge job strips those paths, which left two failure modes:
lcov: ERROR: no valid records found→ job fails → noe2e-coverageartifact → the Slack report silently drops its E2E line (what you see after feat: image compositor node with PSD-style layer editor #14809).js.stripe.com/dahlia/stripe.js, fully covered) → E2E reported as 100% (e2e-coverageartifacts drop from ~350 KB to ~28 KB). That is the source of the "GOAL REACHED: E2E test coverage hit 100%" messages.Replaying the current script against the real 28 KB artifact reproduces the Slack message exactly (
E2E: 68.5% → 100.0% (+31.5%)); with this change the same input produces no post.The only source-mapped E2E artifacts after 2026-07-30 came from PR branches not yet rebased past #14209 — hence the decay from ~170/day to zero rather than a clean cutover.
Note the stored
e2e-coverage-baselinecurrently holds the bogus 100%, so the first run after this merges will look like a large regression and post nothing; the baseline self-heals on that same run.