b5d3fd14bb
MLB statsapi + WNBA ESPN live boxscores -> per-player current values
(live:{sport}:{date} TTL 90s, /api/live/:sport + Next proxy). Pure
propState math (HIT / ON PACE / NEEDS N / HOLDS / LINE PASSED — never
red in-progress), attachLiveProgress strip join on nameKey+statType,
proximity-to-hit slate float, StatStrip LiveTracker in the ROW-GRAMMAR
outcome slot (spec amended + lock test updated). Grades never change
in-game — tracking, labeled as such. 2698 -> 2757 tests, web build 0.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
94 lines
6.4 KiB
Markdown
94 lines
6.4 KiB
Markdown
# VYNDR — ROW-GRAMMAR.md v1.0
|
||
### The row grammar law. Density is unlimited when grammar is fixed: every element is DATA with ONE meaning in the SAME slot on every row of its type. Locked by `tests/unit/rowGrammar.test.js` — a slot-order change that isn't a deliberate spec amendment fails the suite.
|
||
|
||
## 1. THE LAW
|
||
1. **One meaning per element.** A mark (dot, chip, strikethrough, color) means exactly one thing, everywhere it appears.
|
||
2. **One slot per element.** The same element renders in the same position on every row of its type. A reader who learns one row has learned every row.
|
||
3. **All data is mono** (`var(--mono)` / `.mono`) with `tabular-nums` where numbers align. Data never glitches.
|
||
4. **No truncation, ever, of a player name, a game time, or a pitcher line.** Rows wrap or stack; they do not ellipsize identity or schedule facts. (`text-overflow: ellipsis` is banned on those elements.)
|
||
5. **Absent beats wrong.** A slot with no real data renders nothing — never a placeholder value, never a fabricated zero.
|
||
|
||
## 2. CANONICAL PROP-ROW SLOT ORDER
|
||
Every prop row (StatStrip snapshot mode, and any future surface that renders a
|
||
graded prop inline) reads left → right in this fixed order:
|
||
|
||
```
|
||
[1 identity] [2 viability] [3 stat+line+side] [4 market context] [5 model output] [6 outcome] [7 actions] [8 provenance]
|
||
```
|
||
|
||
| slot | contents | notes |
|
||
|---|---|---|
|
||
| 1 identity | player name · team · archetype badge | strip header — name appears ONCE per strip (S42 law) |
|
||
| 2 viability | lineup chip (CONFIRMED / NOT IN LINEUP / PROJ) · injury chip | real feeds only; absent feeds → no chips |
|
||
| 3 stat+line+side | `TB O1.5` | white, mono — the subject of the row |
|
||
| 4 market context | best-price dot · movement chip (STEAM ▲ / VALUE ▲) | what the MARKET is doing, before what the model says |
|
||
| 5 model output | revision strikethrough (original grade) → current grade badge | history then present: `A̶ B` reads "was A, now B" |
|
||
| 6 outcome | live TRACKING mark (`1/2 TB · ▲6th` + progress bar + state chip), then settled chip (✓ HIT / ✕ MISS / PUSH + actual) | S11 amendment: live progress is a PROTO-OUTCOME and lives in this slot; the two are mutually exclusive (a settled prop shows only the settled chip). Once settled, actions (slot 7) disappear — the bet is over |
|
||
| 7 actions | parlay `+` · BOOK IT ⟶ | suppressed when live, dead or settled (the pre-game market for a locked line closes at first pitch) |
|
||
| 8 provenance | `Graded 2h ago at -115` | the receipt, always last |
|
||
|
||
**Sub-line (stat + market context, one line under the row, in this order):**
|
||
`[last-10 dot strip] [line-movement sparkline] [current-line delta]`
|
||
- Each sub-line element renders only when its real data exists (dots need a
|
||
real game log; the sparkline needs ≥3 captured history points; the delta
|
||
needs a previous snapshot). Zero real data → no sub-line.
|
||
|
||
**Strip header order (slot 1 + 2):** name → team → archetype → viability
|
||
chips. Identity is one contiguous run; status chips follow it.
|
||
|
||
## 3. COLOR LAW — one meaning per color
|
||
| color | meaning | examples |
|
||
|---|---|---|
|
||
| **signal green** `--g-a` / `--hit` | edge / best / confirmed-positive | grade-A badge, best-price dot, VALUE chip, HIT chip, CONFIRMED lineup, delta TOWARD, CLV beat, dot-strip filled ● (cleared the line) |
|
||
| **amber** `--amber` | caution / steam / building | STEAM chip, GTD injury, delta AWAY, RECORD BUILDING, SYNC at 1.5× |
|
||
| **red** `--miss` | settled-negative truth ONLY: miss / dead / stale / faded close | MISS chip, NOT IN LINEUP, OUT, SYNC STALE, CLV faded |
|
||
| **dim** `--text-1/2` | absent / projected / neutral | PROJ lineup, awaiting copy, PUSH, dot-strip hollow ○ (didn't clear) |
|
||
|
||
Red is never used for mere movement-against or a lower price — those are amber
|
||
(caution) and plain (fact). The line-movement sparkline is therefore green when
|
||
the net move is TOWARD the graded side, amber when net AGAINST, dim when flat —
|
||
never red (nothing has settled).
|
||
|
||
**S11 amendment — live TRACKING marks (slot 6 proto-outcomes):** green =
|
||
already-cleared over (HIT ✓, filled), on-pace over, or an under still holding;
|
||
amber = NEEDS N or an under whose line has been passed. An IN-PROGRESS prop is
|
||
NEVER red — red stays reserved for the settled miss and the NOT-IN-LINEUP dead
|
||
read. The read is locked pre-game and never re-grades; every live card carries
|
||
"TRACKING — read locked pre-game" exactly once (specs/LIVE-TRACKING.md).
|
||
|
||
## 4. MARK LAW — the micro-vocabulary
|
||
- **● / ○ dot strip** — last 10 games vs TONIGHT'S locked line, newest first.
|
||
Filled green = that game's stat cleared the line; hollow dim = it didn't.
|
||
Real game logs only; no log → no dots.
|
||
- **sparkline** — the REAL captured line over time (intraday refresh history,
|
||
{t, line} points, capped 24). Never rendered under 3 real points.
|
||
- **strikethrough** — a dead or superseded model read (NOT IN LINEUP grade,
|
||
revised-from grade). The original is preserved, struck, never deleted.
|
||
- **▲ ▼** — line movement direction (market fact). **✓ ✕** — settled result.
|
||
- **glow** — A-tier only (NORTH STAR rule). Chrome may glitch; data never.
|
||
|
||
## 5. MOBILE STACKING (≤390px physics)
|
||
- A prop row WRAPS (`flexWrap`) — slots keep their order, overflowing slots
|
||
continue on the next visual line. Order is never re-shuffled for width.
|
||
- The sub-line always stacks BELOW its row, full width.
|
||
- Strip header wraps after the identity run; viability chips may drop to a
|
||
second line but stay ahead of the stats run.
|
||
- Wide data grids (`game-lines-grid`) scroll horizontally inside their own
|
||
container; the page never scrolls horizontally.
|
||
- Names, game times, and pitcher lines wrap to a new line rather than
|
||
truncate (law §1.4).
|
||
|
||
## 6. AUDIT (Session 6, A1 board) — violations found and fixed
|
||
1. **MovementChip rendered AFTER the grade** (market context inside the model
|
||
slot). Moved to slot 4, before the revision/grade pair.
|
||
2. **ViabilityChips rendered between team and archetype**, splitting the
|
||
identity run. Moved after the archetype badge (identity → viability).
|
||
3. `fade-up` keyframe started at `opacity: 0` — violating the S33 "entrance
|
||
keyframes floor at the visible state" rule (a paused frame was invisible,
|
||
and the hero LCP paint was delayed by the animation). Floored at `.6`.
|
||
Everything else already conformed: best-price dot precedes the grade, the
|
||
outcome chip suppresses actions, provenance is last, awaiting rows carry the
|
||
honest schedule copy.
|
||
|
||
— ROW-GRAMMAR v1.0 · July 2026 —
|