android: the handoff — the pending rounds, the pipeline, and what is unverified
Everything written this session that has not been through the device: rounds 43 to 48 (each patch adversarially verified, 43's transient-notice expectation fixed), a partial round 49, the pipeline scripts, the Android Auto design and the icon comparison mock. Also the two harness changes that were never A/B'd — adaptive waits, which may only shorten a declared wait and never lengthen it, and a ship that runs the mock walk and the deploy at the same time. The A/B and its 255-step baseline are in handoff/tools; main stays at what the phone has actually walked.
This commit is contained in:
1 parent
867fd42972
commit
9f0601027c
400 files changed
+26401
-3
No files matched your search
@@ -0,0 +1,75 @@
|
||||
The launch itself had never been measured. The bundle the phone loads is
|
||||
`mobile.html` and three chunks: its own (about 300 KB), the shared one
|
||||
(about 130 KB) and a small third (about 27 KB) — roughly 460 KB of JS and
|
||||
57 KB of CSS, all of it eager. The static graph from `src/mobile-main.js`
|
||||
outward is 64 modules and contains no dynamic import at all, so there is one
|
||||
chunk and the phone evaluates every byte of it at every launch. Importing
|
||||
that graph in headless Chrome costs 11.6 ms at full speed and 59.2 ms at a
|
||||
6× CPU throttle.
|
||||
|
||||
The desktop is not riding along, which was checked rather than assumed: of
|
||||
`state.svelte.js`'s 44 long string literals exactly four appear in the
|
||||
chunks the phone loads, and all four are event names it legitimately uses.
|
||||
`heroGpu.js`, `trace.js`, `ImportWindow.svelte`, `TitleBar` and
|
||||
`DebugOverlay` contribute nothing; there is no shader source anywhere in the
|
||||
bundle. The one passenger is the dev mock library
|
||||
(`src/lib/mockLibrary.js`, about 32 KB of the shared chunk), which
|
||||
`src/lib/api.js` and `src/lib/events.js` import unconditionally because
|
||||
`mockInvoke` has to answer synchronously. It costs 6.6 ms of every launch at
|
||||
6× throttle, only 1.4 ms of which is its top-level work — the rest is parse
|
||||
and function definition, which only removing it from the bundle can recover.
|
||||
`import.meta.env.DEV` cannot do that, because the mock walk builds
|
||||
`dist-smoke/` with a plain production `vite build`; getting it out needs a
|
||||
build-mode flag the walk itself would have to pass. Named here rather than
|
||||
taken.
|
||||
|
||||
The boot chain was the expensive half. It is 26 commands the census can see,
|
||||
plus two plugin listeners that register through `@tauri-apps` directly and go
|
||||
past it. Until this round its critical path — the longest chain where each
|
||||
call was issued only after the one before it had answered — was ten deep,
|
||||
because `listen` is an invoke like any other: `loadLibrary` asked for five
|
||||
independent SQLite reads one after another, `bindSlsk` registered eight
|
||||
listeners one after another, and `watchLibrary` and the player's `bindEvents`
|
||||
each did two. They go out in one round now, and the difference is countable
|
||||
rather than felt: ten of those commands used to leave in the shell's own
|
||||
first turn and twenty-three do now, and the critical path is three instead
|
||||
of ten. Measured in a rig that runs the real store modules —
|
||||
both trees, the same onMount script — with the bridge instrumented and the
|
||||
backend's work modelled behind the library's single `conn: Mutex<Connection>`:
|
||||
the same commands both ways, and `lib.loaded` 85 ms → 53 at a 6 ms bridge
|
||||
round trip, 105 → 57 at 12 ms, 148 → 62 at 20 ms. Those are a desktop rig's
|
||||
milliseconds with the round trip swept rather than measured; the structural
|
||||
half holds anywhere, and the phone's own numbers arrive the first time the
|
||||
walk prints `bootMs` and `bootLibMs`.
|
||||
|
||||
Three things were looked at and deliberately left alone. Home's per-artist
|
||||
catalog walk is the deepest chain in the app — `catalog_artist` →
|
||||
`catalog_artist_identity` → `catalog_related`, serially, per followed artist
|
||||
— and that is the pacing, not an oversight: `crates/metadata/src/lib.rs`
|
||||
holds a Deezer budget of 45 requests per 5 s and records the MusicBrainz
|
||||
identity chain at 4–6 requests behind a mandatory 1 req/s gate, 3.7–8.5 s
|
||||
per artist. The follows are read twice at launch (once by `loadLibrary`,
|
||||
once by `loadHome`), and the obvious guard does not work, because Home's
|
||||
effect calls `loadHome(true)` the first time the follows land — one small
|
||||
local read, left for a round that can do it properly. And lazy-loading the
|
||||
one-tab screens (Diagnostics, Import, Browse, Peer, Room, Thread and the
|
||||
importer) is 9% of the source against a real risk of a blank pushed frame,
|
||||
so it is worth about 6 ms at 6× throttle and is not worth a dynamic import
|
||||
yet.
|
||||
|
||||
The instrument is `src/lib/boot.js`: one counter every `invoke` and every
|
||||
`listen` passes, sealed at the first frame the shell paints and never
|
||||
re-opened, so a probe landing a second and a half later still reads the
|
||||
launch. The mock walk holds a budget against it at the Home step and both
|
||||
walks print `bootCalls`, `bootSync`, `bootMs` and `bootLibMs` on every step.
|
||||
`bootSync` is the clause with no clock in it: it is how many of the boot
|
||||
commands left in the shell's own turn, so a chain put back in a queue can
|
||||
only fall under its floor, whatever the machine is doing. Three things the
|
||||
instrument does not do. It counts the app's own traffic, so the media card's
|
||||
and the transfer notice's `addPluginListener` are invisible to it. It counts
|
||||
commands, not bytes, so a later round that adds an import to a shared file
|
||||
can move modules between chunks with nothing failing — that gap is open. And
|
||||
the mock's exact count depends on how much of the first screen has asked for
|
||||
its covers by the time the second frame lands, so the call ceiling is set to
|
||||
catch a regression in kind (a per-artist walk or an index pulled to boot)
|
||||
rather than a handful of calls.
|
||||
Reference in new issue
Block a user