feat(golf): idempotent demo-realism refresh script (Demo University Golf) - #933
feat(golf): idempotent demo-realism refresh script (Demo University Golf)#933njrini99-code wants to merge 1 commit into
Conversation
…y Golf Part of #910 (data-realism portion) — a live click-through of the golf demo account showed messages exactly 1h apart starting 4:00 AM ET, calendar events frozen relative to whenever seed-demo-team-ops.ts last ran (past events still marked "scheduled", a tee time landing at 3 AM from a raw-UTC-as-local-hour bug), ~20 typo'd/casing course_name variants of the team's two real library courses, and CoachHelm reading stale because the newest round was weeks old. scripts/refresh-golf-demo-realism.ts is a REVIEWED-ONLY, dry-run-by-default, re-runnable script strictly scoped to the hard-coded demo team id (with a name/join_code/coach-staff safety assertion before any write) that: (a) re-times team-channel messages to natural coach/player hours (7-9am / 3-6pm ET, varied minutes), preserving relative day-spacing but re-anchored so the newest message lands yesterday; (b) reschedules the team's 12 known events on a rolling day-offset-from-now schedule (6 always past / 6 always future) with ET-correct local hours instead of raw UTC; (c) canonicalizes every Poplar Grove / Golden Horseshoe course_name variant to the exact name + course_id the course library already has for them, leaving every other course untouched; (d) shifts all team rounds forward (uniform, spacing-preserving) once the newest round is more than 5 days stale, so CoachHelm's rolling-window reads and "updated X" copy stay fresh. The date/time math for (a)/(b)/(d) is extracted into src/lib/golf/demo-realism-schedule.ts (pure, no Supabase) so the trickiest part — timezone-correct local hours and spacing-preserving re-anchoring — is unit-tested in isolation (src/lib/golf/__tests__/demo-realism-schedule.test.ts, 20 cases, including a regression lock for the exact 3 AM tee-time bug). Verified read-only against prod via dry run: 15 messages, 12/12 events matched, 22 + 21 rounds canonicalized, 96 rounds due a 5-day forward shift — all correctly scoped to the demo team only. Gates: tsc --noEmit clean, eslint clean, vitest 20/20 new + 311/311 src/lib/golf/ suite green. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01MMdviLDsAg2YYJ8adsM6fg
|
Bugbot is not enabled for your account, so this pull request was not reviewed. Enable Bugbot in the Cursor dashboard to get automatic reviews on future PRs. |
|
ⓘ Qodo reviews are paused because your trial has ended. Ask your workspace admin to add credits to resume reviews. Manage billing |
|
This pull request has been ignored for the connected project Preview Branches by Supabase. |
|
The latest updates on your projects. Learn more about Vercel for GitHub. |
|
Warning Review limit reached
Next review available in: 40 minutes Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available. How can I continue?After more reviews become available, a review can be triggered using the To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews. How do review limits work?CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability. For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window. Please refer docs for additional details. Review details⚙️ Run configurationConfiguration used: Path: .coderabbit.yaml Review profile: ASSERTIVE Plan: Pro Plus Run ID: 📒 Files selected for processing (3)
✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
|
🤖 Mission Control — PR summary What it changes: Adds Area: GolfHelm (demo-data tooling; script is not executed in CI). Risk / reviewers watch:
CI: 4 required gates green. CodeRabbit advisory + |
Problem
A live click-through of the golf demo account (Demo University Golf,
6ecdd1a6-63fe-4beb-b094-00118f334163) surfaced several things that read as obviously fake or stale — the data-realism findings in #910:golf_eventswas seeded with day-offsets relative to wheneverseed-demo-team-ops.tslast ran (mid-June). Real time has moved on, so several "near future" events are now in the past while stillstatus: 'scheduled'— the calendar header says "N upcoming" while the agenda underneath shows April/May dates. Several events also used a raw UTC hour where an Eastern local hour was intended — "Coastal Collegiate Invitational" tees off at 3:00 AM once converted toAmerica/New_York.golf_rounds.course_nameis free text with ~20 typo'd/casing variants of the team's two real library courses —poplar grove,Poplar Grove (real),Poplar Grove GC,Golden horshoe,golden horeshoe,Golden Horseshoe Gold, etc. — instead of the canonicalgolf_coursesrows the course library already has for them.golf_roundsrow is weeks old, so CoachHelm's rolling-window insights and any "updated X ago" copy read stale the moment the demo sits untouched for a few days.Fix
One idempotent, dry-run-by-default script:
scripts/refresh-golf-demo-realism.ts.Poplar Grove/Golden Horseshoecourse_namevariant on the team to the exact name +course_id+ city/state the course library already has for them (ilikeprefix match, scoped toteam_id). Every other course on the team (Pebble Beach, Forest Creek, Savannah Harbor, Jekyll Island, Cardinal, ...) is left untouched — those weren't the courses flagged as messy.golf_rounds.round_dateon the team is more than 5 days old, shifts every team round forward by the same number of days (uniform, spacing-preserving) so the newest round lands ~1 day ago. CoachHelm's rolling-window reads and "updated X" copy freshen automatically since they're computed live offround_date.The date/time math for (a)/(b)/(d) — the trickiest part, timezone-correct local hours and spacing-preserving re-anchoring — is extracted into
src/lib/golf/demo-realism-schedule.ts(pure, no Supabase dependency) so it's unit-testable in isolation, including a regression lock for the exact 3 AM tee-time bug.Scope & safety
--confirmagainst prod after review (dry run is the default — no--confirmflag ⇒ prints the plan, writes nothing).DEMO_TEAM_ID. Every mutating query filters onteam_id = DEMO_TEAM_ID(golf_events,golf_rounds) or a team-owned conversation id resolved from thatteam_id(golf_messages).assertDemoTeamIdentity()reads the team row (name +join_code) and confirms the known demo-coach user is on staff before any write — refuses to run ifDEMO_TEAM_IDno longer points at what's expected.UPDATEagainst rows discovered at runtime — noDELETE, no destructive rewrite. Re-running is always safe: dates/times get recomputed relative to "now" and simply overwrite the same columns.Known gap (documented in the script, not fixed here)
One
golf_roundsrow (qualifier_idset) is loosely coupled to agolf_qualifiers.start_date/end_dateand agolf_eventsrow viatarget_tournament_id. Shiftinground_date(d) does not cascade togolf_qualifiersdates — pre-existing drift there isn't introduced by this script, and fixing that coupling is a separate, more invasive change.Out of scope (other #910 findings, not addressed by this PR)
This PR only covers the data-realism portion of #910. The "18h" → "18 holes" rounds-row copy bug, the roster "No intent" chip, the Courses page image mismatches, and the CoachHelm Brief label-overlap are UI/copy issues unrelated to demo data freshness — tracked separately (see mission-control notes: Wave 2 already covers some #910 copy items; Wave 3 covers the Brief rebuild). Using "Part of #910", not "Fixes #910".
Proposed run cadence
Suggest wiring this as a weekly cron (Monday, same slot the CRM
v_crosswalk → weekly_call_listcron already uses) viascripts/refresh-golf-demo-realism.ts --confirm, since:Alternatively, a manual pre-demo checklist step ("run
refresh-golf-demo-realism.ts --confirmbefore any live walkthrough") is a reasonable lower-effort fallback if cron infra for this isn't wanted yet — the safety assertion + dry-run-by-default make it safe for anyone on the team to run without deep context.Gates (run in the worktree)
Dry run against prod (read-only, confirms scoping + math against real data — no writes):
Not run:
npm run build, browsers/Playwright (per repo policy for this task).🤖 Generated with Claude Code
https://claude.ai/code/session_01MMdviLDsAg2YYJ8adsM6fg