githubnext/chopinPublic

Let's compose rich plans together

Deliver sidebar decision counts across the repository and keep totals ordered

Review of #378 found that live counts reached only the changed document's
room, that an older frame could roll the project total back, that archiving
left the archived document's decisions in the total, and that a mouse click
kept the row action in place of the count after the pointer left.

- Every socket now also subscribes to a repository topic, and session:decisions
  is published there, so a viewer of one document sees another document's
  count and the project total change without opening its room.
- Count frames for a repository, including the frame a joining socket
  receives, are read and sent one at a time, so a later frame never carries an
  older total. The client also drops a frame's total when its document
  revision is older than the one it holds.
- Archive and restore publish the new repository total, and their responses
  carry it, so the archiving client updates its project row without
  refetching the first page.
- The count swaps for the row action only on hover, keyboard focus
  (:focus-visible), or an open actions menu. Focus inside the row still keeps
  the actions focusable, so tabbing from a document link to its actions holds
  focus.

Assistant-model: Claude Opus 5.5 (fast)
Assistant-workflow: inline
Assistant-verification: bun run fix passed: dprint fmt and oxlint --fix, 10 existing warnings, 0 errors
Assistant-verification: bun test failed: 4042 pass, 3 skip, 29 fail, all in scripts/pr-maintenance (commit signing required in this environment); that suite passes 166/166 with GIT_CONFIG commit.gpgsign=false
Assistant-verification: bun unit passed: decision-counts, routes, and sidebar-decision-counts tests (repository topic, total ordering under a delayed read, archive totals, stale frame totals); the topic and ordering tests fail against the previous service.ts
Assistant-verification: bun run types passed: every workspace package and e2e
Assistant-verification: bun run ci passed: dprint, oxlint, tokens, design contract after renewing the navigation-shell owner hash, design record, impeccable
Assistant-verification: playwright e2e passed: e2e/sidebar-decision-counts.e2e.ts 4/4 (pointer-click focus restores the count, keyboard swap, cross-document live update with only the viewer's own room socket)
Assistant-verification: playwright e2e failed: 117 of 118 sidebar-adjacent specs passed; "a long description card stays inside the window" failed (recorded as failing on unmodified main in the previous commit, not re-run on main this round); an earlier run also failed responsive-activity:106 once, which passed on rerun
Co-authored-by: Alex Lavaee <lavaman131@github.com>
ALAlex Lavaee authored
e0759d4Patch
Parent98a8bff
16 files changed+446-67
StackedSplit
apps/server/src/channels/routes.test.ts+38 โˆ’0
apps/server/src/channels/routes.ts+3 โˆ’1
apps/server/src/main.ts+5 โˆ’1
apps/server/src/plan/decision-counts.test.ts+121 โˆ’0
apps/server/src/plan/service.ts+73 โˆ’29
apps/server/src/wire.ts+14 โˆ’0
apps/web/src/api.ts+5 โˆ’2
apps/web/src/document-actions.tsx+21 โˆ’2
apps/web/src/navigation-shell.tsx+4 โˆ’1
apps/web/src/navigation.css+12 โˆ’4
apps/web/src/room-workspace.tsx+1 โˆ’3
apps/web/src/sidebar-decision-counts.test.ts+42 โˆ’3
apps/web/src/use-project-documents.ts+19 โˆ’3
docs/channels.md+12 โˆ’4
e2e/sidebar-decision-counts.e2e.ts+71 โˆ’12
packages/protocol/index.d.ts+5 โˆ’2