# Testing Guide Comprehensive testing procedures and checklists for ThrillWiki. --- ## Testing Philosophy 1. **Manual testing first** - Critical user flows tested manually 2. **Database validation** - Verify data integrity with SQL queries 3. **Error monitoring** - Watch logs during testing 4. **Real-world scenarios** - Test with realistic data 5. **Edge cases** - Test boundary conditions and error states --- ## Manual Testing Checklist ### Authentication Flow **Password Sign In:** - [ ] Sign in with valid credentials - [ ] Sign in with invalid password - [ ] Sign in with non-existent email - [ ] Session persists after page refresh - [ ] Sign out works correctly **OAuth Sign In:** - [ ] Google OAuth flow completes - [ ] Discord OAuth flow completes - [ ] Profile created after first OAuth sign-in - [ ] OAuth profile data synced correctly **MFA Enrollment:** - [ ] Enroll TOTP factor successfully - [ ] QR code displays correctly - [ ] Backup codes generated - [ ] Verify code works - [ ] Invalid code rejected **MFA Challenge:** - [ ] MFA-enrolled user prompted for code on sign in - [ ] Valid code accepted, session upgraded to AAL2 - [ ] Invalid code rejected - [ ] Step-up required for admin actions - [ ] Lock warning shows when AAL2 about to expire ### Submission Flow **Park Creation:** - [ ] Form validation works (required fields, slug format) - [ ] Image upload works (banner, card, gallery) - [ ] Date precision selector works (day, month, year) - [ ] Location search and selection works - [ ] Operator/property owner selection works - [ ] Submission created in moderation queue - [ ] Toast confirmation shows - [ ] No direct write to parks table **Park Editing:** - [ ] Existing park loads in form - [ ] Change detection works (only changed fields submitted) - [ ] Image replacement works - [ ] Submission created with original_data - [ ] Edit appears in moderation queue **Ride Creation:** - [ ] All ride categories work - [ ] Coaster stats editor works (metric only) - [ ] Technical specs editor works - [ ] Former names editor works - [ ] Unit conversion helper displays - [ ] Submission created successfully **Company Creation:** - [ ] Company type selection works - [ ] Person type selection works - [ ] Founded date with precision works - [ ] Logo upload works - [ ] Submission created successfully **Ride Model Creation:** - [ ] Manufacturer required validation works - [ ] Category selection works - [ ] Submission created successfully ### Moderation Queue **Queue Display:** - [ ] All pending submissions show - [ ] Filters work (entity type, status, search) - [ ] Sort options work - [ ] Pagination works - [ ] Stats display correctly **Claiming:** - [ ] Claim submission button works - [ ] Lock acquired (15 minutes) - [ ] Lock status displays - [ ] Another moderator cannot claim - [ ] Lock expires after 15 minutes **Lock Management:** - [ ] Lock timer displays correctly - [ ] Warning shows at 2 minutes remaining - [ ] Extend lock button works - [ ] Lock auto-expires if not extended - [ ] Expired lock shows error state **Review:** - [ ] Submission items display correctly - [ ] Change comparison shows (for edits) - [ ] Dependency visualization works - [ ] Individual item approval works - [ ] Individual item rejection works **Approval:** - [ ] Approve all works - [ ] Selective approval works - [ ] Edge function called successfully - [ ] Entity created/updated in database - [ ] Version created with correct attribution - [ ] Submission status updated to 'approved' - [ ] Lock released - [ ] Notification sent to submitter **Rejection:** - [ ] Rejection reason required - [ ] Reject all works - [ ] Submission status updated to 'rejected' - [ ] Lock released - [ ] Notification sent to submitter ### Versioning System **Version Creation:** - [ ] Version created on entity INSERT - [ ] Version created on entity UPDATE - [ ] Version number increments - [ ] is_current flag set correctly - [ ] created_by set from session variable - [ ] submission_id linked correctly **Version History:** - [ ] All versions display in timeline - [ ] Version details show correctly - [ ] Created by user shows - [ ] Change type badge displays - [ ] Current version marked **Version Comparison:** - [ ] Select two versions - [ ] Compare button enabled - [ ] Diff shows changed fields only - [ ] Old vs new values display - [ ] Foreign key changes resolved to names **Rollback:** - [ ] Rollback button shows (not for current version) - [ ] Rollback creates new submission - [ ] Submission goes to moderation queue - [ ] On approval, new version created ### Image Upload **Upload Flow:** - [ ] Drag & drop works - [ ] File picker works - [ ] Multiple files upload - [ ] Progress indicator shows - [ ] CloudFlare upload succeeds - [ ] Image preview displays - [ ] Caption editor works - [ ] Set as banner works - [ ] Set as card works - [ ] Remove image works - [ ] Blob URLs cleaned up **Error Handling:** - [ ] File too large rejected - [ ] Invalid file type rejected - [ ] Network error handled - [ ] Partial upload failure handled - [ ] Cleanup on error works ### Unit System **Display Conversion:** - [ ] Metric user sees km/h, m, cm - [ ] Imperial user sees mph, ft, in - [ ] Auto-detection sets correct system - [ ] Manual preference change works - [ ] Conversion accurate **Input Validation:** - [ ] Coaster stats only accept metric - [ ] Technical specs enforce metric - [ ] Conversion helper shows correct formula - [ ] Invalid unit rejected ### Date Handling **Date Input:** - [ ] Date picker works (day precision) - [ ] Month picker works (month precision) - [ ] Year input works (year precision) - [ ] Precision selector works - [ ] Date stored as YYYY-MM-DD **Date Display:** - [ ] Day precision: "July 15, 2024" - [ ] Month precision: "July 2024" - [ ] Year precision: "2024" - [ ] Empty date handled gracefully ### Notifications **Subscriber Creation:** - [ ] Novu subscriber created on sign up - [ ] Subscriber ID stored in database - [ ] Profile data synced to Novu **Notification Triggering:** - [ ] Submission approved notification sent - [ ] Submission rejected notification sent - [ ] Review reply notification sent - [ ] Moderation alert sent to moderators **Notification Center:** - [ ] In-app center displays - [ ] Unread count shows - [ ] Mark as read works - [ ] Notification click navigates correctly ### User Roles & Permissions **Role Assignment:** - [ ] Admin can grant moderator role - [ ] Admin can grant admin role - [ ] Only superuser can grant superuser role - [ ] Role revocation works - [ ] Audit log entry created **Permission Checks:** - [ ] User cannot access admin pages - [ ] Moderator can access moderation queue - [ ] Admin can access user management - [ ] Superuser can access all admin features - [ ] MFA required for sensitive actions --- ## Database Validation Queries ### Check Submission Flow ```sql -- Verify no direct writes to entity tables (should be empty if moderation works) SELECT * FROM parks WHERE created_at > NOW() - INTERVAL '1 hour' AND id NOT IN ( SELECT (item_data->>'park_id')::UUID FROM submission_items WHERE item_type = 'park' AND status = 'approved' ); ``` ### Check Versioning ```sql -- Verify version created for recent park update SELECT p.name, pv.version_number, pv.change_type, pv.created_by, pv.submission_id, pv.is_current FROM parks p JOIN park_versions pv ON pv.park_id = p.id WHERE p.updated_at > NOW() - INTERVAL '1 hour' ORDER BY p.id, pv.version_number DESC; ``` ### Check Lock Status ```sql -- Identify stuck locks SELECT id, submission_type, assigned_to, assigned_at, locked_until, status FROM content_submissions WHERE status = 'pending' AND locked_until IS NOT NULL AND locked_until < NOW(); ``` ### Check RLS Policies ```sql -- Test entity table RLS (should fail as non-service role) BEGIN; SET LOCAL ROLE authenticated; INSERT INTO parks (name, slug, park_type) VALUES ('Test Park', 'test-park', 'theme_park'); -- Should fail with permission denied ROLLBACK; ``` --- ## Error Monitoring ### Console Logs Watch browser console for: - [ ] No React errors - [ ] No TypeScript errors - [ ] No 401 Unauthorized errors - [ ] No 403 Forbidden errors - [ ] No 500 Server errors ### Network Tab Monitor API calls: - [ ] All Supabase requests succeed - [ ] Edge function calls return 200 - [ ] CloudFlare uploads succeed - [ ] Realtime subscriptions connected - [ ] No excessive requests (n+1 queries) ### Edge Function Logs Check Supabase logs for: - [ ] No unhandled exceptions - [ ] Request/response logged - [ ] Duration reasonable (<5s) - [ ] No infinite loops --- ## Performance Testing ### Page Load Times - [ ] Homepage loads < 2s - [ ] Park detail loads < 3s - [ ] Moderation queue loads < 3s - [ ] Image heavy pages load < 5s ### Query Performance ```sql -- Slow query detection SELECT query, calls, total_time, mean_time, max_time FROM pg_stat_statements WHERE mean_time > 100 -- Over 100ms average ORDER BY mean_time DESC LIMIT 20; ``` ### Bundle Size ```bash npm run build # Check dist/ folder size # Target: < 1MB initial bundle ``` --- ## User Acceptance Testing ### New User Journey 1. [ ] Sign up with email/password 2. [ ] Verify email (if required) 3. [ ] Complete profile setup 4. [ ] Browse parks 5. [ ] Add ride credit 6. [ ] Write review 7. [ ] Submit new park (goes to moderation) ### Moderator Journey 1. [ ] Sign in with moderator account 2. [ ] View moderation queue 3. [ ] Claim submission 4. [ ] Review submission details 5. [ ] Approve submission 6. [ ] Verify entity live on site 7. [ ] Check version history ### Admin Journey 1. [ ] Sign in with admin account 2. [ ] Complete MFA challenge 3. [ ] View user management 4. [ ] Grant moderator role 5. [ ] View system activity log 6. [ ] Check admin settings --- ## Regression Testing After major changes, re-test: **Critical Paths:** - [ ] Auth flow (sign in, sign up, sign out) - [ ] Submission flow (create park, moderation, approval) - [ ] Version system (create, compare, rollback) - [ ] Image upload (upload, set variants, delete) **Secondary Paths:** - [ ] Search functionality - [ ] Filters and sorting - [ ] User profiles - [ ] Reviews and ratings - [ ] Lists management --- ## Test Data Generation Use the built-in test data generator: ```typescript // Navigate to /admin/settings // Click "Test Data Generator" tab // Select entities to generate // Click "Generate Test Data" ``` Or use the edge function: ```bash curl -X POST https://[project-ref].supabase.co/functions/v1/seed-test-data \ -H "Authorization: Bearer [anon-key]" \ -H "Content-Type: application/json" \ -d '{ "parks": 10, "rides": 50, "companies": 5, "users": 20 }' ``` --- ## Bug Reporting Template ```markdown **Bug Description:** Clear description of the issue **Steps to Reproduce:** 1. Go to... 2. Click on... 3. Enter... 4. Observe... **Expected Behavior:** What should happen **Actual Behavior:** What actually happens **Environment:** - Browser: Chrome 120 - OS: macOS 14 - User Role: Moderator - Device: Desktop **Console Errors:** ``` [Paste console errors] ``` **Screenshots:** [Attach screenshots if relevant] **Database State:** [Relevant database records if applicable] ``` --- **See Also:** - [PHASE_5_TESTING.md](./PHASE_5_TESTING.md) - Original testing plan - [TEST_DATA_GENERATOR.md](./TEST_DATA_GENERATOR.md) - Test data generation - [TROUBLESHOOTING.md](./TROUBLESHOOTING.md) - Common issues and solutions