"use client"; import { useState, useEffect } from "react"; import Link from "next/link"; import { useParams, useRouter } from "next/navigation"; import { ChevronLeft, Trash2, Loader, Pencil, ChevronDown, ChevronUp, } from "lucide-react"; import { WorkoutWithSets } from "@/types"; import { formatSetsSummary } from "@/lib/formatSets"; function buildSetSummary(set: { weight?: number | null; weightUnit?: string | null; reps?: number | null; rpe?: number | null; notes?: string | null; durationSeconds?: number | null; distance?: number | null; calories?: number | null; }) { const parts: string[] = []; if (set.weight) parts.push(`${set.weight} ${set.weightUnit === "kg" ? "kg" : "lbs"}`); if (set.reps) parts.push(`${set.reps} reps`); if ((set as any).durationSeconds) parts.push(`${(set as any).durationSeconds}s`); if ((set as any).distance) parts.push(`${(set as any).distance} mi`); if ((set as any).calories) parts.push(`${(set as any).calories} cal`); if (set.rpe) parts.push(`RPE ${set.rpe}`); if (set.notes) parts.push(set.notes); return parts.length > 0 ? parts.join(" · ") : "No data"; } export default function WorkoutDetailPage() { const params = useParams(); const router = useRouter(); const [workout, setWorkout] = useState(null); const [loading, setLoading] = useState(true); const [deleting, setDeleting] = useState(false); const [expandedExercise, setExpandedExercise] = useState(null); const workoutId = params.id as string; useEffect(() => { const fetchWorkout = async () => { try { const response = await fetch(`/api/workouts/${workoutId}`); if (!response.ok) throw new Error("Failed to fetch"); const data = await response.json(); setWorkout(data); } catch (error) { console.error("Error fetching workout:", error); } finally { setLoading(false); } }; fetchWorkout(); }, [workoutId]); const handleDelete = async () => { if (!confirm("Are you sure you want to delete this workout?")) return; setDeleting(true); try { const response = await fetch(`/api/workouts/${workoutId}`, { method: "DELETE" }); if (!response.ok) throw new Error("Failed to delete"); router.push("/main/workouts"); } catch (error) { console.error("Error deleting workout:", error); alert("Failed to delete workout"); setDeleting(false); } }; if (loading) { return (
); } if (!workout) { return (
Back

Workout not found

); } // Format date const date = new Date(workout.date); const formattedDate = date.toLocaleDateString("en-US", { weekday: "short", month: "short", day: "numeric", year: "numeric", }); // Group sets by exercise (preserving order) const exerciseGroups: Array<{ exerciseId: string; exerciseName: string; sets: typeof workout.setLogs }> = []; const seen = new Set(); for (const set of workout.setLogs) { if (!seen.has(set.exercise.id)) { seen.add(set.exercise.id); exerciseGroups.push({ exerciseId: set.exercise.id, exerciseName: set.exercise.name, sets: workout.setLogs.filter((s) => s.exercise.id === set.exercise.id), }); } } // Build post-workout stats const stats: string[] = []; if (workout.durationMinutes) stats.push(`${workout.durationMinutes} min`); if (workout.difficulty) stats.push(`Difficulty ${workout.difficulty}/10`); return (
{/* Header */}

{workout.name || "Unnamed Workout"}

{formattedDate}

{/* Exercises — compact collapsible cards */} {exerciseGroups.map((group) => { const isExpanded = expandedExercise === group.exerciseId; const setsWithData = group.sets.filter((s) => s.reps || s.weight); const summary = formatSetsSummary(setsWithData) || `${group.sets.length} set${group.sets.length !== 1 ? "s" : ""}`; return (
{/* Exercise header */} {/* Expanded sets — same style as locked SetRow */} {isExpanded && (
{group.sets.map((set) => (
{set.setNumber}

{buildSetSummary(set)}

))}
)}
); })} {/* Post-workout info (notes, duration, difficulty) */} {(workout.notes || stats.length > 0) && (
{stats.length > 0 && (

{stats.join(" · ")}

)} {workout.notes && (

{workout.notes}

)}
)} {/* Edit button at bottom */}
Edit Workout
); }