Skip to content

fix(plan): a restored plan_review card drew checkboxes as checked but counted 0 - #19

Merged
Its-My-Work merged 1 commit into
mainfrom
fix/plan-review-restore-selection
Sep 22, 2026
Merged

Its-My-Work merged 1 commit into
mainfrom
fix/plan-review-restore-selection

Conversation

@Its-My-Work

Copy link
Copy Markdown
Owner

Reported live with a screenshot: a reloaded chat showed every task checked, yet the footer said "0 of 26 selected" and "Approve to Backlog (0)" stayed disabled — clicking a checkbox did nothing.

Cause

The default selection ("everything without a lint error of its own") was only ever computed in _prRender (the live WS path). planReviewCardHtml's per-task checkbox and its footer/button read _planSelections[messageId] two different ways when it didn't exist yet: a checkbox fell back to true, the count/button fell back to an empty Set — checked boxes, zero count. The DB-restore render path (a page reload) never goes through _prRender, so it always hit this; worse, it also never set _planReviews[messageId], so a click's _prTogglePlanTask found no review to look up dependents in and silently no-op'd.

Fix

  • planReviewCardHtml now computes and stores the default selection itself, once; every place in the function reads that one value. Self-healing — any caller gets a consistent card.
  • The DB-restore call site sets _planReviews[id] before rendering, same as _prRender always did.
  • Fixed alongside: _prRerenderTasks updated the checkboxes and the button after a click, but never the "N of M selected" line next to it — stale after the first click. Now updates all three.

Tests

render/plan-review.test.mjs: a card rendered with no pre-seeded selection (the exact restore scenario) now has checkboxes/count/button agreeing, and _planSelections gets populated as a side effect; a toggle right after a restore-only render actually mutates the Set. Checked live in real headless Chrome against a real seeded DB row and a real page load: before the fix reproduced verbatim, after the fix consistent from the first render and correct after a click. Whole npm test suite green.

🤖 Generated with Claude Code

https://claude.ai/code/session_01Y2ZSHUdJHqVsvSNQ5ZeQ3f

… counted 0

Found live: a reloaded chat showed every task checked, yet the footer said "0
of 26 selected" and "Approve to Backlog (0)" stayed disabled — clicking a
checkbox did nothing.

Cause: the default selection ("everything without a lint error of its own")
was only ever computed in _prRender (the live WS path). planReviewCardHtml's
per-task checkbox and its footer/button read that same default two DIFFERENT
ways when _planSelections[messageId] didn't exist yet: a checkbox fell back
to `true`, the count/button fell back to an empty Set — checked boxes, zero
count. The DB-restore render path (a page reload) never went through
_prRender at all, so it always hit this inconsistent fallback; worse, it
also never set _planReviews[messageId], so a click's _prTogglePlanTask found
no review to look up dependents in and silently no-op'd.

- planReviewCardHtml now computes and STORES the default selection itself,
  once, and every place in the function reads that one value — no more two
  fallbacks to drift apart. Self-healing: any caller gets a consistent card,
  restored or live.
- The DB-restore call site now sets _planReviews[id] BEFORE rendering, same
  as _prRender always did, so a click on a restored card works.
- Fixed alongside: _prRerenderTasks (runs after every click) updated the
  checkboxes and the button but never the "N of M selected" line next to it
  — it went stale after the very first click. Now updates all three.

Tests: render/plan-review.test.mjs — a card rendered with NO pre-seeded
selection (the exact restore scenario) now has checkboxes, count and button
agreeing, and _planSelections gets populated as a side effect; a toggle
right after a restore-only render actually mutates the Set. Checked live in
real headless Chrome against a real seeded DB row and a real page load:
before the fix reproduced verbatim (2 checked boxes, "0 of 2 selected",
button disabled(0)); after the fix, consistent from the first render and
correct after a click ("1 of 2 selected", button (1), unchecked box stays
unchecked) — screenshots in the 2026-09-22 session scratchpad.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Y2ZSHUdJHqVsvSNQ5ZeQ3f
@Its-My-Work
Its-My-Work merged commit 5d5b0c7 into main Sep 22, 2026
1 check passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant