Skip to content

Conversation

@AlexVOiceover
Copy link
Contributor

Overview

Implements comprehensive individual apprentice attendance tracking with advanced cohort filtering, bulk selection, and interactive UI enhancements. This delivers the complete AP-25 feature for monitoring apprentice attendance patterns and early intervention.


Changes

Core Attendance Features

  • Added /admin/attendance/apprentices route with server-side data loading
  • Created ApprenticeAttendanceCard component for individual metrics display
  • Implemented attendance rate calculations and trend indicators
  • Added detailed apprentice view (/admin/attendance/apprentices/[id]) with full history

Enhanced Cohort Management

  • Smart cohort grouping by prefix (FAC29, FAC30, etc.) with newest first
  • Dedicated MLX cohort group always positioned at bottom
  • Clickable group headers for bulk cohort selection/deselection
  • Visual indicators for full/partial selection states

"Not Coming" Status System

  • Added new attendance status for apprentices to mark absence in advance
  • API endpoint /api/checkin/not-coming with proper validation
  • Idempotent backend handling to prevent duplicate submissions
  • Allow transition from "Not Coming" to "Checked In" but not vice versa

Check-in Flow Improvements

  • Fixed Svelte 5 reactivity issues causing UI state desync
  • Refactored button styles into consistent shared CSS classes
  • Added double-click prevention with proper loading states
  • Enhanced guest check-in with event selection and validation

Testing & Data Quality

  • Comprehensive test suite for attendance functions
  • Fixed attendance filtering logic to use JavaScript instead of Airtable formulas
  • Improved event attendance counting with proper cohort calculations
  • Added support for cross-cohort event attendance tracking

TL;DR

  1. New admin routes: Access attendance tracking via /admin/attendance/apprentices
  2. Cohort filtering: Use group headers to select entire cohort families (FAC29, MLX, etc.)
  3. "Not Coming" feature: Apprentices can now pre-register absences through check-in flow
  4. Environment update: Add RESEND_FROM_EMAIL to your .env.local if missing

Gallery

Cohort Selection with Smart Grouping

FAC31 (2 cohorts) ✓
├── FAC31.1 ✓  
└── FAC31.2 ✓

FAC30 (3 cohorts) ◐
├── FAC30.1 ✓
├── FAC30.2 ○
└── FAC30.3 ○

MLX (4 cohorts) ○
├── MLX Cohort 1 ○
├── MLX Cohort 2 ○
└── ...

Check-in Status Progression

Not Coming → Check In Instead ✓
Check In → Checked In ✓ (one-way)

…lection

- Add cohort selection UI on initial page load (no data fetch until selected)
- Support multiple cohort selection with visual feedback
- Add "Show All Apprentices" option with warning modal for slow fetch
- Add loading spinner overlay during data fetch
- Create ApprenticeAttendanceCard component for displaying metrics
- Add detail page for individual apprentice attendance history
- Add getApprenticeAttendanceHistory function with tests
- Sort cohort tiles alphabetically
- Add AttendanceHistoryEntry type
Events are now included in apprentice history if:
1. Event is for apprentice's cohort (marked Missed if no attendance)
2. Apprentice has attendance record (regardless of cohort)
3. All events if apprentice has no cohort
…irtable formula

Airtable filterByFormula with linked fields matches display values,
not record IDs. Changed to fetch all attendance and filter in JS
to correctly match apprentice by record ID.
The hasUserCheckedIn function was using Airtable filterByFormula with
linked record field IDs, which doesn't work correctly. Changed to fetch
all attendance and filter in JavaScript to properly match by record ID.

This fixes the bug where users could check in multiple times to the
same event.
Events on the checkin page are now sorted with the most recent
events at the top for better UX.
- Added blue gradient header with welcome message
- Display logged-in user's name and email
- Improved visual hierarchy for the checkin page
- Fixed lint error in attendance filter
Display current attendance as X/Y badge on each event card,
showing how many have checked in out of expected attendees.
For public events without cohorts, display "X checked in"
instead of hiding the attendance badge entirely.
- Grey out and disable check-in button for events not on today
- Add tooltip explaining "Check-in opens on the day of the event"
- Check-in is only available on the same day as the event
- Show all events with matching code for today and tomorrow
- Display events in a list similar to authenticated user view
- Tomorrow's events shown but disabled (can't check in yet)
- Guest selects event before entering details
- Added getEventsByCode function to fetch multiple events
- Add purple gradient header for guest mode to differentiate from authenticated
- Make event cards full width to match authenticated view
- Center forms, success messages, and instructions
- Center link buttons and login prompt
- Add 'Not Coming' to ATTENDANCE_STATUSES type and stats interface
- Add getUserAttendanceForEvent() and markNotComing() functions
- Create /api/checkin/not-coming endpoint (apprentices only)
- Update /api/checkin to handle Not Coming → Check In transition
- Add red 'Not Coming' button on checkin page with proper disabled states
- Show orange badge and styled card when marked as not coming
- Update stats components to display 'Not Coming' count
- Add orange color styling for 'Not Coming' in admin views
…selection

- Group cohorts by prefix (FAC29, FAC30, etc.) with newer cohorts on top
- Place all MLX cohorts in a single group at the bottom
- Add clickable group headers for bulk selection/deselection
- Show visual indicators for group selection states (none, partial, all)
- Maintain individual cohort selection functionality
- Fix Svelte state reference warning
- Fix Svelte 5 reactivity issue with events not updating in UI after check-in
- Make events reactive using $state instead of direct data.events mutation
- Add double-click prevention for both check-in and not-coming buttons
- Refactor button styles to use consistent shared CSS classes
- Improve loading states with clearer text ("Marking not coming...")
- Add debugging console logs for check-in success tracking
- Ensure one-way check-in flow (no "Not Coming" after check-in)
@AlexVOiceover AlexVOiceover marked this pull request as ready for review January 6, 2026 11:37
@AlexVOiceover AlexVOiceover merged commit 05effcc into main Jan 6, 2026
2 checks passed
@AlexVOiceover AlexVOiceover deleted the feature/ap-25-individual-apprentice-attendance-view branch January 7, 2026 21:24
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.

2 participants