Press n or j to go to the next uncovered block, b, p or k for the previous block.
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 | 'use client' import { useEffect, useRef, useState } from 'react' import type { Socket } from 'socket.io-client' import { createSocket } from '@/lib/socket' import { useQueryClient } from '@tanstack/react-query' import { invalidateForEvent } from '@/lib/classroom/query-invalidations' import type { EnrollmentApprovedEvent } from '@/lib/classroom/socket-events' /** * Hook for real-time player enrollment updates via WebSocket * * When a student becomes fully enrolled in a classroom (both teacher and parent approved), * this hook receives the event and invalidates the enrolled classrooms query so the * dropdown updates without requiring a page reload. * * @param playerId - The player ID to subscribe to enrollment notifications for * @returns Whether the socket is connected */ export function usePlayerEnrollmentSocket(playerId: string | undefined): { connected: boolean } { const [connected, setConnected] = useState(false) const socketRef = useRef<Socket | null>(null) const queryClient = useQueryClient() useEffect(() => { if (!playerId) return // Create socket connection const socket = createSocket({ reconnection: true, reconnectionDelay: 1000, reconnectionAttempts: 5, }) socketRef.current = socket socket.on('connect', () => { console.log('[PlayerEnrollmentSocket] Connected') setConnected(true) // Join the player channel for enrollment notifications socket.emit('join-player', { playerId }) }) socket.on('disconnect', () => { console.log('[PlayerEnrollmentSocket] Disconnected') setConnected(false) }) // Listen for enrollment completed event (student fully enrolled in a classroom) socket.on('enrollment-approved', (data: EnrollmentApprovedEvent) => { console.log( '[PlayerEnrollmentSocket] Enrollment completed for classroom:', data.classroomName ) invalidateForEvent(queryClient, 'enrollmentCompleted', { classroomId: data.classroomId, playerId, }) }) // Cleanup on unmount return () => { socket.emit('leave-player', { playerId }) socket.disconnect() socketRef.current = null } }, [playerId, queryClient]) return { connected } } |