Verify six app seams and record Phase 4 performance measurements
This commit is contained in:
@@ -2,7 +2,7 @@
|
||||
|
||||
Source: `cd4a25a`, 587,029 bytes. Acorn 8 parses classic scripts with source ranges; eslint-scope 8 resolves lexical references, including shadowing. Outside references are references outside the declaration’s owning top-level statement, plus unresolved references from other frontend classic scripts. Property names and strings are not lexical references. Browser globals and other scripts’ globals remain available. Positions below refer to this source, before extraction.
|
||||
|
||||
Reproduce: `npm install --prefix perf/.tmp/analysis --no-audit --no-fund acorn@8 eslint-scope@8`, then run `node perf/analyze-app.cjs`. Analysis tools are development-only; no frontend/server import is added.
|
||||
Reproduce: `npm install --prefix perf/.tmp/analysis --no-audit --no-fund acorn@8 eslint-scope@8`, then run `node perf/analyze-app.cjs cd4a25a`. Analysis tools are development-only; no frontend/server import is added.
|
||||
|
||||
## Measured candidate ranking
|
||||
|
||||
@@ -414,3 +414,34 @@ Outside references use app line numbers or `file:line`; imports name other app b
|
||||
| bootViewFromUrl | 12531 | 391 | view, render, URL_VIEWS | 12625 |
|
||||
| bootSearchFromUrl | 12545 | 414 | els | 12626 |
|
||||
| boot | 12563 | 11475 | WEB, APP_VERSION, perfMark, perfMeasure, webFetch, SaveQueue, API, DEFAULT_SETTINGS, data, view, current, abA, abB, cachedIds, downloading, $, els, persist, ProfileSecret, profileHeaders, syncOnLaunch, updateProfileStatus, adoptSharedPlaylistFromUrl, startPlaylistInboxWatch, adoptProfileFromUrl, syncMuteIcon, toast, uid, applyAppearance, refreshCachedIds, startCacheResyncWatch, warmOfflineThumbs, preload, preloadPlaylist, preloadPinnedPlaylists, Player, wirePlayerEvents, updatePlayBtn, Notes, Remote, Transition, CatalogSync, Recommendations, Presenter, Share, EqRender, PiP, EQ, SectionRail, Party, updateBottomChrome, updateQueueBadge, playNext, updateLoopRepeatButtons, playPrev, isServiceModeOpen, renderSidebar, exportToDevice, render, slim, wireShortcutHelp, showModal, closeModal, setupClassicLayout, setupPortraitPwaWatcher, setupViewportAnchorGuard, wireUI, setAbA, setAbB, clearAb, saveAbMarkers, updateAbUI, renderSmartSidebar, checkAutoBackup, checkBuildTag, pollBuildTag, checkUpdateOutcome, registerServiceWorker, bootShareFromUrl, bootViewFromUrl, bootSearchFromUrl | 12734 |
|
||||
|
||||
## Final cuts and review
|
||||
|
||||
Exactly six seams shipped: 3c9a24a (eager shell/shared renderers), 5fb9564
|
||||
(Presenter), 8e7fa19 (Remote), 94ea211 (Watch party), 0475a18 (Share/External),
|
||||
b335f95 (Stats view). 2c50035 handles lazy-entry failures without rejected UI
|
||||
navigation promises. Final app.js: 408,473 bytes; net removal 178,556 bytes
|
||||
(30.4169%), including 2,976 bytes of facade/call-site overhead.
|
||||
|
||||
Original bytes moved, independently counted from UTF-8 AST source slices:
|
||||
98,378 eager renderer/shell/rail; 9,492 Presenter; 30,421 Remote;
|
||||
22,833 Party; 13,334 Share/External; 7,074 Stats view. Published files include
|
||||
headers/registry wrappers. Shared functions retain classic global lexical access;
|
||||
new UI definitions evaluate safely before data/$/els/Player initialization.
|
||||
|
||||
Self-review against master §6/6b: all new files belong to explicit manifest
|
||||
groups and legacy SHELL; source JSON matches assets.json; core scripts load first;
|
||||
required eager features stay parsed. Player, Transition, Wave, EQ/level rendering,
|
||||
queue, persistence, tracking and sleep bodies have exact source fingerprint tests.
|
||||
Transport internals move intact; entry button bindings move to core facades to
|
||||
avoid duplicate listeners. Inbound APIs remain short; synchronous boolean/hooks
|
||||
never become promises. Boot URL/session triggers remain; no banner/cache-header
|
||||
rule is changed. Executing groups remain pinned; no disposal/handoff or live
|
||||
replacement is introduced. Contract/N-1 safeguards remain tested by existing
|
||||
unit/integration checks.
|
||||
|
||||
Deliberately left: Notes/editor, service mode, playlist mutations, persistence,
|
||||
player/queue/boot, audio watchdogs/EQ/sleep, Gestures, video editor/export glue and
|
||||
other candidates beyond six seams. Settings paint moves to views-core but remains
|
||||
eager. Now-playing metadata mutations inside Player stay there to honor the
|
||||
untouched-playback constraint; their DOM, action paint and mini bar are eager.
|
||||
|
||||
119
plans/phase4-verification.md
Normal file
119
plans/phase4-verification.md
Normal file
@@ -0,0 +1,119 @@
|
||||
# Phase 4 verification
|
||||
|
||||
The served frontend is build `c3dbdd7039db`, source delivery commit `2c50035`.
|
||||
`phase4-final-2026-10-08.json` records parent b335f95 because the review fix was
|
||||
uncommitted when its scratch tree was copied; that tree includes exactly the
|
||||
frontend subsequently committed as 2c50035. The isolated cold result records both
|
||||
2c50035 and the build tag. Earlier phase result files were restored after harnesses
|
||||
wrote their default paths; Phase 4 copies retain the actual new run evidence.
|
||||
|
||||
## Six green seams
|
||||
|
||||
| Commit | Seam | Original bytes moved | Frontend tests | Server tests | Both-engine cached smoke / hidden timers |
|
||||
|---|---|---:|---:|---:|---|
|
||||
| 3c9a24a | Eager shell/views/section rail | 98,378 | 192 | 183 | Pass |
|
||||
| 5fb9564 | Presenter | 9,492 | 193 | 183 | Pass |
|
||||
| 8e7fa19 | Remote client | 30,421 | 194 | 183 | Pass |
|
||||
| 94ea211 | Watch party | 22,833 | 195 | 183 | Pass |
|
||||
| 0475a18 | Share/External | 13,334 | 196 | 183 | Pass |
|
||||
| b335f95 | Stats view | 7,074 | 197 | 183 | Pass |
|
||||
| 2c50035 | Lazy-entry rejection handling | — | 198 | 183 | Pass |
|
||||
|
||||
After every seam, `node --test frontend/*.test.js`, `bun install` then `bun run test`
|
||||
in server, `node perf/hidden-timers.mjs`, and `node perf/seams.mjs --browser all`
|
||||
ran. Server tests used PATH="$PWD/../perf/.tmp/test-venv/bin:$PATH" so yt-dlp
|
||||
worker tests also ran, without skips. Logs are in gitignored perf/.tmp; representative
|
||||
actual output:
|
||||
|
||||
```
|
||||
ℹ tests 198
|
||||
ℹ pass 198
|
||||
ℹ fail 0
|
||||
ℹ skipped 0
|
||||
```
|
||||
|
||||
Server totals across its isolated test processes: 183 pass, 0 fail, 0 skip.
|
||||
|
||||
```
|
||||
chromium {"browser":"chromium","checked":["shell","presenter","remote","party","share","stats"],"offlineNetworkRequests":0,"errors":[]}
|
||||
webkit {"browser":"webkit","checked":["shell","presenter","remote","party","share","stats"],"offlineNetworkRequests":0,"errors":[]}
|
||||
Result: ALL ASSERTIONS PASSED
|
||||
```
|
||||
|
||||
The cache smoke stops Bun and blocks its proxy, then tests home playlists and eager
|
||||
Settings, Presenter blank/pair validation, Remote pair form/close, Party local UI,
|
||||
Share timestamp editing, External uploaded-media sheet/M3U, populated Stats view,
|
||||
and a rejected entry action. Network relays are still required to connect parties
|
||||
or remotes; offline verification proves cached code/UI, not offline relay service.
|
||||
Existing lazy harness passes offline layouts, first-use, Settings extensions,
|
||||
contract guards, pinned instances and update-during-playback on both engines.
|
||||
|
||||
One review smoke WebKit process terminated during concurrent browser checks; an
|
||||
isolated rerun and the final expanded both-engine smoke passed. Initial harness
|
||||
fixture errors (incorrect Settings selector, absent VM helper, timestamp format,
|
||||
hidden list pane) were corrected to exercise actual UI; no product tests were
|
||||
removed or weakened.
|
||||
|
||||
## Measurements
|
||||
|
||||
Actual commands:
|
||||
|
||||
```
|
||||
node perf/baseline.mjs --runs 1 --browser all --profile lte --scenario all --out perf/results/phase4-final-2026-10-08.json --compare perf/results/after-phase0-2026-10-07.json
|
||||
node perf/baseline.mjs --runs 3 --browser chromium --profile lte --scenario cold --out perf/results/phase4-cold-isolated-2026-10-08.json --compare perf/results/after-phase0-2026-10-07.json
|
||||
```
|
||||
|
||||
Full reduced run overlapped other checks; its Chromium long tasks were 495 ms.
|
||||
Repeat cold-only runs with no concurrent tests produced 297/274/275 ms (median
|
||||
275). Keep both results: neither is rewritten. WebKit lacks the long-task API.
|
||||
Historical Phase 0 is five-run data; these reduced measurements are directional.
|
||||
|
||||
| Metric | Phase 0 Chromium / WebKit | Phase 3 Chromium / WebKit | Phase 4 Chromium / WebKit |
|
||||
|---|---:|---:|---:|
|
||||
| Initial compressed JS/CSS | 276,414 / 338,940* | 221,307 / 274,813 | 210,419 / 255,200 |
|
||||
| Cold boot ms | 10,480 / 3,290 | 7,193 / 3,293 | 7,010** / 2,977 |
|
||||
| Cold FCP ms | 1,572 / 1,100 | 1,356 / 2,467 | 1,352** / 2,401 |
|
||||
| Cold long-task ms | 454 / unavailable | 287 / unavailable | 275** / unavailable |
|
||||
| Warm boot ms | 692 / 139 | 419 / 81 | 467 / 132 |
|
||||
| Offline boot ms | 259 / 137 | 166 / 84 | 180 / 90 |
|
||||
| Core app update wire bytes | 611,338 / 680,822 | 159,905 / 194,026 | 125,795 / 147,259 |
|
||||
| Inactive CSS blocking-readiness bytes | 611,476 / 680,831 | 29,724 / 28,082 | 30,263 / 28,713 |
|
||||
| Feature edit through actual idle cache fill | — | — | 33,408 / 41,364 |
|
||||
|
||||
*Matched Phase 0 source reconstructed in Phase 3; historical JSON lacks initial
|
||||
bytes. **Isolated three-run Chromium cold median. Other Phase 4 numbers are the
|
||||
one-run both-browser suite. Warm counters include unfinished initial idle caching.
|
||||
CSS readiness excludes its later background payload; it is not full update cost.
|
||||
WebKit first paint still fails the master no-regression target. Full five-run
|
||||
comparisons belong to Phase 5. Native iPhone timing/audio/quota is unverified.
|
||||
|
||||
Actual feature-update output:
|
||||
|
||||
```
|
||||
run 1/1: 33408 bytes, 8 reqs, dur=1376ms
|
||||
run 1/1: 41364 bytes, 7 reqs, dur=1358ms
|
||||
```
|
||||
|
||||
Only presenter.js application payload transfers (3,118 / 3,587 compressed bytes).
|
||||
Totals include changed stamped index, manifest, version checks, sw.js checks and
|
||||
WebKit's 1,954-byte sync-core worker import. No app.js, unchanged core views,
|
||||
fonts, icons or CSS transfer. The benchmark asserts this rather than inferring it
|
||||
from the lower total. Final app.js is 408,473 versus 587,029 bytes: −178,556,
|
||||
−30.4169%; original code moved totals 181,532, facade overhead 2,976 bytes.
|
||||
|
||||
## Migration, rollback and owner checks
|
||||
|
||||
Both engines pass b77938a migration with lossy/stalling and unthrottled proxies:
|
||||
122 cached SHELL entries, one banner and exactly one user-initiated reload,
|
||||
21 legacy URL checks, N-1 open-tab continuity, offline boot, playback guard,
|
||||
eviction repair and incremental refresh. Result JSON records the real runs.
|
||||
No automatic activation/reload or live singleton replacement is added.
|
||||
|
||||
Rollback ASSET_SYNC=0 and ASSET_HASHING=0 use the existing legacy path; commands
|
||||
and results are in perf/README.md and perf/results. No new feature flag.
|
||||
Revert an individual seam to restore its previous parsing behavior.
|
||||
|
||||
Owner must verify a real iPhone PWA: warm feature first-use, selected/offline layout,
|
||||
Presenter/Remote/Party sessions, update guard/override, locked audio 30 minutes,
|
||||
interruption/resume, saved OPFS music surviving cache quota pressure. Nothing was
|
||||
pushed, merged or deployed.
|
||||
Reference in New Issue
Block a user