B5 — Planner board: card-face indicators (scan in 1s) #413

Closed
opened 2026-04-27 00:03:01 +00:00 by claude-desktop · 0 comments
Collaborator

As an operator,
I want the card face to show stage, agent, PR state, round, stall age, and design-review status,
so that I can read board health at a glance without opening each card.

Card face today shows title + status (running/queued/in_review/idle_assigned/unassigned) + agent. Operators flip into the issue detail to find PR state, round, and stall age. This story consolidates those signals onto the card face and adds a density toggle.

Acceptance criteria

Card face layout

  • Top-left: stage icon (triage / spec / impl / review / merged) — 14 px, semantic colour from tokens.css.
  • Top-right: PR state pill (draft grey / open accent / merged success / none hidden); links to the PR URL on click. Pill uses rounded-pill per apps/web/CLAUDE.md.
  • Bottom-left: agent avatar (24 px) + login (@dev, @reviewer-2); empty slot when unassigned.
  • Bottom-right: stall age (2h, 3d); text-warning once past the per-stage threshold from docs/label-routing.md, text-error past 2× threshold (matches B8).
  • Round counter badge (R3) when round > 1, anchored next to the stage icon.
  • Design-review badge ( accept / reject) when present, between the agent avatar and the stall age.

Density toggle

  • Toolbar segmented control Density: [compact | default | detailed], persisted in localStorage (key board.density).
  • compact — single line: stage icon + title + stall age. No agent, no PR, no badges.
  • default — full layout above.
  • detailed — adds last-event line ("queued 2h ago") under the agent row.

Backend — extend GET /board response per card

  • Add pr_state: "draft" | "open" | "merged" | "none" (derive from existing PR-state derivation in apps/server/src/domain/views/...).
  • Add round: number (default 0).
  • Add stalled_for_ms: number (already known server-side from pipeline_stage events; surface it).
  • Add stage: "triage" | "spec" | "impl" | "review" | "merged" if not already on the card response.
  • Add last_event_label: string | null for the detailed density mode (e.g. "queued", "running on @dev").

Tests

  • board-card.test.tsx: renders all six face elements at default density given a fully-populated card.
  • board-card.test.tsx: compact density renders only stage / title / stall age.
  • board-card.test.tsx: warning + error stall colour at threshold + 2× threshold.
  • Server test: /board response includes the new fields with realistic values.

Out of scope

  • Card cover images (no artwork to show).
  • Inline-editable card fields (handled by B4 letter shortcuts).
  • Per-instance stall thresholds (use per-stage threshold today).

References

  • Spec: docs/specs/board-rework.md §5 B5 + §6.
  • Per-stage stall thresholds: docs/label-routing.md.
  • Token classes (bg-triage, text-warning, rounded-pill, etc.): apps/web/src/styles/tokens.css + apps/web/CLAUDE.md.
  • PR state derivation logic: search apps/server/src/domain/views/ for pr_state or pull.state.

Dependencies

  • Lands first in the implementation order — pure projection, server response is additive, unblocks B6/B7/B8 visuals.

Suggested first commit

feat(board): card-face indicators — stage / PR / agent / round / stall + density toggle

**As an** operator, **I want** the card face to show stage, agent, PR state, round, stall age, and design-review status, **so that** I can read board health at a glance without opening each card. Card face today shows title + status (`running`/`queued`/`in_review`/`idle_assigned`/`unassigned`) + agent. Operators flip into the issue detail to find PR state, round, and stall age. This story consolidates those signals onto the card face and adds a density toggle. ## Acceptance criteria ### Card face layout - [ ] **Top-left**: stage icon (`triage` / `spec` / `impl` / `review` / `merged`) — 14 px, semantic colour from `tokens.css`. - [ ] **Top-right**: PR state pill (`draft` grey / `open` accent / `merged` success / `none` hidden); links to the PR URL on click. Pill uses `rounded-pill` per `apps/web/CLAUDE.md`. - [ ] **Bottom-left**: agent avatar (24 px) + login (`@dev`, `@reviewer-2`); empty slot when unassigned. - [ ] **Bottom-right**: stall age (`2h`, `3d`); `text-warning` once past the per-stage threshold from `docs/label-routing.md`, `text-error` past 2× threshold (matches B8). - [ ] **Round counter badge** (`R3`) when round > 1, anchored next to the stage icon. - [ ] **Design-review badge** (`✓` accept / `✗` reject) when present, between the agent avatar and the stall age. ### Density toggle - [ ] Toolbar segmented control `Density: [compact | default | detailed]`, persisted in `localStorage` (key `board.density`). - [ ] `compact` — single line: stage icon + title + stall age. No agent, no PR, no badges. - [ ] `default` — full layout above. - [ ] `detailed` — adds last-event line (`"queued 2h ago"`) under the agent row. ### Backend — extend `GET /board` response per card - [ ] Add `pr_state: "draft" | "open" | "merged" | "none"` (derive from existing PR-state derivation in `apps/server/src/domain/views/...`). - [ ] Add `round: number` (default 0). - [ ] Add `stalled_for_ms: number` (already known server-side from `pipeline_stage` events; surface it). - [ ] Add `stage: "triage" | "spec" | "impl" | "review" | "merged"` if not already on the card response. - [ ] Add `last_event_label: string | null` for the detailed density mode (e.g. `"queued"`, `"running on @dev"`). ### Tests - [ ] `board-card.test.tsx`: renders all six face elements at `default` density given a fully-populated card. - [ ] `board-card.test.tsx`: `compact` density renders only stage / title / stall age. - [ ] `board-card.test.tsx`: warning + error stall colour at threshold + 2× threshold. - [ ] Server test: `/board` response includes the new fields with realistic values. ## Out of scope - Card cover images (no artwork to show). - Inline-editable card fields (handled by B4 letter shortcuts). - Per-instance stall thresholds (use per-stage threshold today). ## References - Spec: `docs/specs/board-rework.md` §5 B5 + §6. - Per-stage stall thresholds: `docs/label-routing.md`. - Token classes (`bg-triage`, `text-warning`, `rounded-pill`, etc.): `apps/web/src/styles/tokens.css` + `apps/web/CLAUDE.md`. - PR state derivation logic: search `apps/server/src/domain/views/` for `pr_state` or `pull.state`. ## Dependencies - **Lands first** in the implementation order — pure projection, server response is additive, unblocks B6/B7/B8 visuals. ## Suggested first commit `feat(board): card-face indicators — stage / PR / agent / round / stall + density toggle`
Sign in to join this conversation.
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set.

Reference
charles/claude-hooks#413
No description provided.