All checks were successful
Build and Push Docker Image / build (push) Successful in 9m57s
- Phase 2 complete: all 3 plans done (DASH-01 through DASH-07 fulfilled) - REQUIREMENTS.md: marked DASH-05, DASH-06, DASH-07 complete - ROADMAP.md: Phase 2 updated to Complete (3/3 plans) - STATE.md: advanced to Phase 2 complete, added 3 new decisions
105 lines
4.8 KiB
Markdown
105 lines
4.8 KiB
Markdown
---
|
|
phase: 02-ranking-dashboard-ui
|
|
plan: 03
|
|
subsystem: ui
|
|
tags: [react, trpc, dialog, shadcn, ranking, advance-projects, batch-reject]
|
|
|
|
# Dependency graph
|
|
requires:
|
|
- phase: 02-02
|
|
provides: Full RankingDashboard with drag-and-drop, AI vs override badges, Sheet detail panel, saveReorderMutation
|
|
provides:
|
|
- Advance Top N dialog wired to trpc.round.advanceProjects with per-category N inputs
|
|
- Batch-reject checkbox in advance dialog wired to trpc.roundEngine.batchTransition
|
|
- DASH-07 disabled state: Advance button disabled while saveReorderMutation.isPending
|
|
affects: []
|
|
|
|
# Tech tracking
|
|
tech-stack:
|
|
added: []
|
|
patterns:
|
|
- "pendingReorderCount useRef pattern: onMutate increments, onSettled decrements — provides belt-and-suspenders for rapid drag scenarios alongside isPending reactive signal"
|
|
- "Parallel mutation from single handler: advanceMutation.mutate + batchRejectMutation.mutate fired in same handleAdvance — fire-and-forget both, each handles own onSuccess/onError"
|
|
|
|
key-files:
|
|
created: []
|
|
modified:
|
|
- src/components/admin/round/ranking-dashboard.tsx
|
|
|
|
key-decisions:
|
|
- "Advance button disabled via saveReorderMutation.isPending (reactive) not pendingReorderCount.current (ref, non-reactive) — ref used for belt-and-suspenders coverage, boolean state for actual UI"
|
|
- "topNStartup + topNConceptual === 0 disables the Advance button inside the dialog — prevents no-op advance calls"
|
|
- "batchRejectMutation fired conditionally (only if includeReject and rejectIds.length > 0) — avoids empty batch call"
|
|
|
|
patterns-established:
|
|
- "Per-category N inputs with min/max clamping via Math.max/Math.min on parseInt — prevents out-of-range values"
|
|
- "Preview section in dialog: live count of advancing/rejecting projects — feedback before confirmation"
|
|
|
|
requirements-completed: [DASH-05, DASH-06, DASH-07]
|
|
|
|
# Metrics
|
|
duration: 5min
|
|
completed: 2026-02-27
|
|
---
|
|
|
|
# Phase 2 Plan 03: Advance Top N Dialog + Batch-Reject Summary
|
|
|
|
**Advance Top N dialog with per-category numeric inputs, optional batch-reject checkbox, and disabled state tied to pending reorder mutations — completing the full advancement workflow for the RankingDashboard**
|
|
|
|
## Performance
|
|
|
|
- **Duration:** ~5 min
|
|
- **Started:** 2026-02-27T08:51:01Z
|
|
- **Completed:** 2026-02-27T08:56:00Z
|
|
- **Tasks:** 1
|
|
- **Files modified:** 1
|
|
|
|
## Accomplishments
|
|
|
|
- DASH-05: Admin can click "Advance Top N" button to open a dialog, enter a number N per category, and advance the top N projects from each category to the next round
|
|
- DASH-06: Admin can enable "Also batch-reject non-advanced projects" checkbox in the dialog — fires batchTransition for non-advanced projects; toasts use `.succeeded.length` per MEMORY.md
|
|
- DASH-07: Advance button is disabled while `saveReorderMutation.isPending` is true (reorder in flight) and when no snapshot exists
|
|
- pendingReorderCount ref added to saveReorderMutation (onMutate++, onSettled--) for belt-and-suspenders reorder tracking
|
|
- Full dialog: per-category N inputs with range clamping, live preview of advance/reject counts, cancel/confirm buttons
|
|
- Both mutations invalidate `roundEngine.getProjectStates` on success to refresh downstream state
|
|
- TypeScript strict mode: 0 errors; build: PASSED
|
|
|
|
## Task Commits
|
|
|
|
| Task | Name | Commit | Files |
|
|
|------|------|--------|-------|
|
|
| 1 | Add Advance Top N dialog + batch-reject to RankingDashboard | a6f3945 | src/components/admin/round/ranking-dashboard.tsx |
|
|
|
|
## Files Created/Modified
|
|
|
|
- `src/components/admin/round/ranking-dashboard.tsx` — Added Dialog, Input, Label imports; pendingReorderCount ref; advanceMutation; batchRejectMutation; handleAdvance; Advance Top N button; Dialog JSX (681 lines total, +197 insertions)
|
|
|
|
## Decisions Made
|
|
|
|
- **Advance button disabled state uses `saveReorderMutation.isPending`** (reactive) as the primary signal, not `pendingReorderCount.current` (useRef is not reactive — React won't re-render on ref mutation). The ref still provides belt-and-suspenders for rapid multi-drag scenarios but is not the gating signal.
|
|
- **topNStartup + topNConceptual === 0** disables the confirm button inside the dialog — prevents a no-op advance call when both inputs are zero.
|
|
- **batchRejectMutation fires conditionally** — only when `includeReject` is true AND `rejectIds.length > 0`. Avoids sending an empty projectIds array to the mutation.
|
|
|
|
## Deviations from Plan
|
|
|
|
None — plan executed exactly as written.
|
|
|
|
## Issues Encountered
|
|
|
|
None.
|
|
|
|
## User Setup Required
|
|
|
|
None - no external service configuration required.
|
|
|
|
## Next Phase Readiness
|
|
|
|
- All 7 DASH requirements (DASH-01 through DASH-07) completed across plans 01-03
|
|
- Phase 2 (Ranking Dashboard UI) is fully complete
|
|
- Phase 3 (Notification Templates) or Phase 4 (Juror Criterion Progress) can begin next
|
|
- Full build and typecheck pass with 0 errors
|
|
|
|
---
|
|
*Phase: 02-ranking-dashboard-ui*
|
|
*Completed: 2026-02-27*
|