import { useState, useEffect } from 'react';
import { useNavigate, Link } from 'react-router-dom';
import toast from 'react-hot-toast';
import Layout from '../components/layout/Layout';
import { useAuth } from '../contexts/AuthContext';
import { dashboardAPI, matchesAPI } from '../services/api';
import { connectSocket, disconnectSocket, getSocket } from '../services/socket';
import HeatBadges from '../components/heats/HeatBadges';
import {
Calendar,
MapPin,
Users,
MessageCircle,
Video,
Star,
Check,
X,
Loader2,
Clock,
ChevronRight,
Inbox,
Send,
} from 'lucide-react';
const DashboardPage = () => {
const { user } = useAuth();
const navigate = useNavigate();
const [data, setData] = useState(null);
const [loading, setLoading] = useState(true);
const [error, setError] = useState('');
const [processingMatchId, setProcessingMatchId] = useState(null);
useEffect(() => {
loadDashboard();
// Connect to socket for real-time updates
const token = localStorage.getItem('token');
if (token && user) {
connectSocket(token, user.id);
const socket = getSocket();
if (socket) {
socket.on('match_request_received', handleMatchRequest);
socket.on('match_accepted', handleMatchAccepted);
socket.on('match_cancelled', handleRealtimeUpdate);
socket.on('new_message', handleRealtimeUpdate);
}
}
return () => {
const socket = getSocket();
if (socket) {
socket.off('match_request_received', handleMatchRequest);
socket.off('match_accepted', handleMatchAccepted);
socket.off('match_cancelled', handleRealtimeUpdate);
socket.off('new_message', handleRealtimeUpdate);
}
disconnectSocket();
};
}, [user]);
const handleMatchRequest = (data) => {
toast.success(`New match request from ${data.requesterUsername || 'someone'}!`, {
icon: '📨',
});
loadDashboard();
};
const handleMatchAccepted = (data) => {
toast.success('Match accepted! You can now chat.', {
icon: '🎉',
});
loadDashboard();
};
const loadDashboard = async () => {
try {
setLoading(true);
const result = await dashboardAPI.getData();
setData(result);
} catch (err) {
console.error('Failed to load dashboard:', err);
setError('Failed to load dashboard');
} finally {
setLoading(false);
}
};
const handleRealtimeUpdate = () => {
loadDashboard();
};
const handleAcceptMatch = async (matchSlug) => {
try {
setProcessingMatchId(matchSlug);
await matchesAPI.acceptMatch(matchSlug);
toast.success('Match accepted! You can now chat.', { icon: '🎉' });
await loadDashboard();
} catch (err) {
console.error('Failed to accept match:', err);
toast.error('Failed to accept match. Please try again.');
} finally {
setProcessingMatchId(null);
}
};
const handleRejectMatch = async (matchSlug) => {
if (!confirm('Are you sure you want to decline this request?')) return;
try {
setProcessingMatchId(matchSlug);
await matchesAPI.deleteMatch(matchSlug);
toast.success('Request declined.');
await loadDashboard();
} catch (err) {
console.error('Failed to reject match:', err);
toast.error('Failed to decline request. Please try again.');
} finally {
setProcessingMatchId(null);
}
};
const handleCancelRequest = async (matchSlug) => {
if (!confirm('Are you sure you want to cancel this request?')) return;
try {
setProcessingMatchId(matchSlug);
await matchesAPI.deleteMatch(matchSlug);
toast.success('Request cancelled.');
await loadDashboard();
} catch (err) {
console.error('Failed to cancel request:', err);
toast.error('Failed to cancel request. Please try again.');
} finally {
setProcessingMatchId(null);
}
};
if (loading) {
return (
Loading dashboard...
Welcome back, {user?.firstName || user?.username}!
Dashboard
Browse all
View all
{/* Incoming Requests */}
{hasIncoming && (
Your heats:
@{partner.username}
{event.name}
{/* Status Indicators */}@{requester.username}
{event.name}
{requesterHeats?.length > 0 && (@{recipient.username}
{event.name}
{description}
{action}