phase: 13_llm_page_and_decode_rate
All green. Final verification summary:
**Verified / implemented (phase 13 final pass)**
- All 4 tasks already in `complete/`; this was the verification pass. Confirmed the CSS rhythm rules (`#strip`, `#banners:empty ~ #fleet`) are served and pinned, `data/logs/NOTES-decode-spike.md` names the mechanism, and the phase-07/04 surfaces still pass their pins.
- **Found and fixed a residual defect in this phase's own code**: a stalled fetch stamps its body with the poll's *finish* time, so that sample anchors every window for the rest of the span; the jump gate "confirmed" a jump measured from that same anchor → live gufo rows 232.28 tok/s (one request at ~50) + a decaying 146/114/95 tail, repeated at 200.6. `rates.py::_publish` now requires an **independent anchor** (`_pending` stores the base sample's ts; the hold continues until it ages out). Pinned by `test_a_held_jump_is_not_confirmed_by_a_window_on_the_same_anchor` + `test_gufo_a_stale_scrape_body_never_becomes_a_rate_above_the_engine` (both fail on task 03's gate).
- Re-verified live after a dev-server restart: 10 min / 540 signed-in `/api/llm/snapshot` polls + read-only SQLite pass; **0 values > 300, 0 without a `Δ<window>` label**; 0 post-fix stored rows over the ceiling except the two pre-fix-shape rows above.
**Tests / lint (exact, all 100 % green)**
- `bash .agents/validate.sh` → **EXIT=0**; `uv run pytest --cov --cov-fail-under=94` → **1195 passed, 11 skipped, coverage 98.70 %**; `ruff check src tests agent` → All checks passed; `pyright` → 0 errors; `node --check` clean; repo hygiene clean.
- `uv run pytest -m live --live` → **11 passed / 0 failed**. `/api/health` → **all nine sources ok**.
**Completion criteria**
- Fleet/strip + head/fleet gap with screenshots (`llm-fleet-spacing{,-top,-banner-case}.png`) — met (CSS unchanged this pass, pinned on served bytes).
- Task-02 findings file names the confirmed mechanism — met.
- `test_rates.py`/`test_llm_source.py` pin label-set, both window bounds and the always-honest `Δ` — met (+2 new pins).
- Sustained watch under the recorded ceiling (300 tok/s) — met (worst 203.05, all labelled).
- Full suite + validate green; no phase-07/04 behaviour change — met.
**Documentation**
- README: `RATE_WINDOW_SECONDS` row now states the hold/confirm rule (only change needed; rest verified consistent).
- AGENTS.md: `rates.py` bullet + gap 9 rewritten (residual closed *and* the remaining sub-8× skew measured, root-caused to gap 4, explicitly not fixed by inventing a new threshold).
- **Fleet facts changed under this pass and were corrected**: operator added driveripper's bearer token → `host:driveripper`/`disks:driveripper` `ok`, live suite 9/2→11/0; but driveripper reads **identity only, zero SMART numbers** (root `smartctl` gives 55 °C/14 %; `/dev/nvme0`, `/dev/ng0n1`, `/dev/bsg/*` are root-only; its unit is `DevicePolicy=auto`, not the installer's `strict`). Evidence appended to `data/logs/NOTES-agent-install.md` + `NOTES-decode-stable.md`.
**Notable decisions / deviations**
- Did **not** add a span-relative window floor: that would re-decide task 03's pinned `MIN_WINDOW_SECONDS` and its "in-bounds diluted row publishes" test. Recorded as the next phase's call, with the root cause left at gap 4 / `14_store_performance` (the ~10 s stall).
- No live fleet change made (read-only probes + one dev-server restart). Fixtures deliberately not re-captured (no parse change, task 02 proved no shape drift). Dependency-currency advisory left untouched (no dependency moved in this phase): certifi/fastapi/starlette/websockets have newer releases.
**Next pending phase:** `.agents/phases/todo/14_store_performance` (then `15_agent_mtls`).
This commit is contained in:
@@ -2421,6 +2421,96 @@ def test_llm_fleet_block_colours_no_number(client) -> None:
|
||||
"the fleet block's head row lost its styling"
|
||||
|
||||
|
||||
#: Elements the browser treats as empty, so they never open a nesting level.
|
||||
_VOID_TAGS = {"meta", "link", "br", "img", "input", "hr", "source", "track", "wbr"}
|
||||
|
||||
|
||||
def _depth_at(html: str, needle: str) -> int:
|
||||
"""How deeply the `needle` sits inside `<main>` (1 = a direct child of it).
|
||||
|
||||
The `~` in `#banners:empty ~ #fleet` only resolves between **siblings**, so the gap rule
|
||||
depends on the markup as much as on the stylesheet. Counting tags is enough here and keeps
|
||||
the check on the served bytes: no HTML parser, no dependency, and comments are already
|
||||
gone by the time `_code` hands the page over.
|
||||
"""
|
||||
body = html[html.index("<main>"):html.index(needle, html.index("<main>"))]
|
||||
depth = 0
|
||||
for closing, tag, _attrs, self_closed in re.findall(
|
||||
r"<(/?)([a-zA-Z][\w-]*)([^>]*?)(/?)>", body):
|
||||
if self_closed or tag.lower() in _VOID_TAGS:
|
||||
continue
|
||||
depth += -1 if closing else 1
|
||||
return depth
|
||||
|
||||
|
||||
def test_llm_section_stack_keeps_the_shared_vertical_rhythm(client) -> None:
|
||||
"""Fleet block → engine summaries → engine panels sit the shared `.85rem` apart.
|
||||
|
||||
`TODO.md:4`: the fleet section had no spacing between it and the engine summaries. Every
|
||||
boundary below it was already handled inline — the section under `#strip` carries
|
||||
`margin-top:.85rem` — so `#fleet` and `#strip` skipped the rhythm and the top of the page
|
||||
read as one unbroken wall. Measured in Chromium at the 16px root (`data/logs/`
|
||||
`llm-fleet-spacing*.png`), before → after:
|
||||
|
||||
| gap | before | after |
|
||||
|-----|--------|-------|
|
||||
| `#fleet` → `#strip` | **0 (flush)** | 13.59px |
|
||||
| `#strip` → engine panels | 13.59px | 13.59px |
|
||||
| banner slot → `#fleet`, no banner | 13.59px | 13.59px |
|
||||
| banner slot → `#fleet`, one banner up | 13.59px | 13.59px (`margin-top: 0px`) |
|
||||
|
||||
One rendered distance moves, and it is the one the operator named. What the *shape* of the
|
||||
two rules buys is that no other state can put it back:
|
||||
|
||||
* `#strip`'s gap is **unconditional**, because below two engines `#fleet` is `[hidden]`
|
||||
(`display:none !important`, so it contributes nothing) and the strip is then the first
|
||||
visible section: the 13.59px below the banner slot in that state is now the strip's own
|
||||
margin rather than one borrowed from a slot above it, which is what `#fleet ~ #strip`
|
||||
would have been;
|
||||
* `#fleet`'s gap is guarded by `#banners:empty`, so the block owns its top gap exactly when
|
||||
nothing occupies the slot above it, and a banner's own `margin-bottom:.85rem` stays the
|
||||
single gap under it. An unguarded `#fleet { margin-top }` is a second rule for one gap:
|
||||
margin collapsing hides it at `.85rem`/`.85rem` today, and it doubles the moment either
|
||||
margin is changed. The empty slot keeps its inline bottom margin, so head → fleet stays
|
||||
the 1rem + .85rem the other two banner pages (`/`, `/ups`) already render.
|
||||
|
||||
Pinned on the served bytes because a stylesheet "cleanup" that drops either rule is
|
||||
invisible in a diff and only shows up as a page that reads worse.
|
||||
"""
|
||||
raw = _css(client)
|
||||
section = _css_section(raw, "fleet totals")
|
||||
assert "#strip { margin-top: .85rem; }" in section, \
|
||||
"the fleet block and the engine summaries render flush again (TODO.md:4)"
|
||||
assert "#banners:empty ~ #fleet { margin-top: .85rem; }" in section, (
|
||||
"the gap above the fleet block stopped belonging to the block: a banner-less page "
|
||||
"would then have it only as long as the empty banner slot keeps its inline margin")
|
||||
|
||||
# one rule per element: a second one (or an unguarded `#fleet`) is the double gap
|
||||
css = _code(raw)
|
||||
for element, expected in (("#strip", {"#strip"}),
|
||||
("#fleet", {"#banners:empty ~ #fleet"})):
|
||||
selectors = {s.strip() for s in re.findall(rf"([^{{}}]*{element}[^{{}}]*)\{{", css)}
|
||||
assert selectors == expected, (
|
||||
f"dash.css styles {element} with {sorted(selectors)} — exactly one rule, the "
|
||||
"guarded one, or the page grows a double gap or loses the single one")
|
||||
|
||||
html = _code(client.get("/llm").text)
|
||||
for element in ("banners", "fleet", "strip"):
|
||||
assert _depth_at(html, f'id="{element}"') == 1, (
|
||||
f"`#{element}` is no longer a direct child of <main>, so the `~` gap rule cannot "
|
||||
"match: rewrite the selectors for the new structure instead of dropping the gap")
|
||||
assert html.index('id="banners"') < html.index('id="fleet"') < html.index('id="strip"') \
|
||||
< html.index('id="engines"'), "the section stack was re-ordered"
|
||||
|
||||
# the inline half of the rhythm, which the two rules are written around
|
||||
assert 'style="margin-bottom:.85rem"' in html[:html.index('id="fleet"')], (
|
||||
"#banners lost the inline bottom margin that is the banner → fleet gap, and today the "
|
||||
"only thing spacing the page head from the block")
|
||||
after_strip = html[html.index('id="strip"'):]
|
||||
assert after_strip.count('style="margin-top:.85rem"') == 3, \
|
||||
"a section below the strip lost the inline gap the strip's rule hands off to"
|
||||
|
||||
|
||||
# ---- the `/llm` gufo slot grid (phase 07 task 04) -------------------------
|
||||
#
|
||||
# `llm_monitor`'s slot cards (`index.html` ~L1179), rebuilt against the capture instead of a
|
||||
|
||||
Reference in New Issue
Block a user