"use client";
import React, { useState, useEffect } from "react";
import { useParams, useRouter } from "next/navigation";
import { cmsApi, Course } from "@/lib/api";
import { ArrowLeft, Save, Settings as SettingsIcon, BookOpen, Calendar, Clock, Download, Upload } from "lucide-react";
const DEFAULT_CERTIFICATE_TEMPLATE = `
Certificate of Completion
This is to certify that
{{student_name}}
has successfully completed the course
{{course_title}}
with a score of {{score}}%
Dated
{{date}}
`;
import CourseEditorLayout from "@/components/CourseEditorLayout";
export default function CourseSettingsPage() {
const { id } = useParams() as { id: string };
const router = useRouter();
const [course, setCourse] = useState(null);
const [passingPercentage, setPassingPercentage] = useState(70);
const [certificateTemplate, setCertificateTemplate] = useState("");
const [loading, setLoading] = useState(true);
const [saving, setSaving] = useState(false);
const [pacingMode, setPacingMode] = useState<'self_paced' | 'instructor_led'>("self_paced");
const [startDate, setStartDate] = useState("");
const [endDate, setEndDate] = useState("");
const [exporting, setExporting] = useState(false);
const [importing, setImporting] = useState(false);
useEffect(() => {
const fetchCourse = async () => {
try {
const data = await cmsApi.getCourse(id);
setCourse(data);
setPassingPercentage(data.passing_percentage || 70);
setCertificateTemplate(data.certificate_template || DEFAULT_CERTIFICATE_TEMPLATE);
setPacingMode(data.pacing_mode || "self_paced");
setStartDate(data.start_date ? new Date(data.start_date).toISOString().split('T')[0] : "");
setEndDate(data.end_date ? new Date(data.end_date).toISOString().split('T')[0] : "");
} catch (err) {
console.error("Failed to load course", err);
} finally {
setLoading(false);
}
};
fetchCourse();
}, [id]);
const handleSave = async () => {
setSaving(true);
try {
const updated = await cmsApi.updateCourse(id, {
passing_percentage: passingPercentage,
certificate_template: certificateTemplate,
pacing_mode: pacingMode,
start_date: startDate ? new Date(startDate).toISOString() : undefined,
end_date: endDate ? new Date(endDate).toISOString() : undefined
});
setCourse(updated);
alert("Course settings updated successfully!");
} catch (err) {
console.error("Failed to save", err);
alert("Failed to save settings");
} finally {
setSaving(false);
}
};
const handleExport = async () => {
setExporting(true);
try {
const data = await cmsApi.exportCourse(id);
const blob = new Blob([JSON.stringify(data, null, 2)], { type: 'application/json' });
const url = URL.createObjectURL(blob);
const a = document.createElement('a');
a.href = url;
a.download = `course_${id}_export.json`;
document.body.appendChild(a);
a.click();
document.body.removeChild(a);
URL.revokeObjectURL(url);
} catch (err) {
console.error("Export failed", err);
alert("Error al exportar el curso");
} finally {
setExporting(false);
}
};
const handleImport = async (e: React.ChangeEvent) => {
const file = e.target.files?.[0];
if (!file) return;
setImporting(true);
try {
const text = await file.text();
const data = JSON.parse(text);
const newCourse = await cmsApi.importCourse(data);
alert(`Curso importado con éxito: ${newCourse.title}`);
router.push(`/courses/${newCourse.id}/settings`);
} catch (err) {
console.error("Import failed", err);
alert("Error al importar el curso. Asegúrate de que el formato sea válido.");
} finally {
setImporting(false);
if (e.target) e.target.value = ''; // Reset input
}
};
if (loading) return (
);
if (!course) return (
Course not found.
);
return (
{/* Header */}
router.back()}
className="p-2 hover:bg-white/10 rounded-full transition-colors"
>
Course Settings
Configure general course properties and certificates for {course?.title}
{saving ? "Saving..." : "Save Changes"}
{/* Passing Percentage Section */}
Passing Percentage
Students must achieve at least this percentage to pass the course.
{/* Performance Tiers Preview */}
Performance Tiers Preview
Reprobado:
0% - {Math.max(0, passingPercentage - 1)}%
Rendimiento Bajo:
{passingPercentage}% - {passingPercentage + 9}%
Rendimiento Medio:
{passingPercentage + 10}% - {passingPercentage + 15}%
Buen Rendimiento:
{passingPercentage + 16}% - 90%
{/* Course Pacing Section */}
Pacing Mode
setPacingMode('self_paced')}
className={`flex-1 p-4 rounded-2xl border-2 transition-all text-left ${pacingMode === 'self_paced' ? 'border-blue-500 bg-blue-500/10' : 'border-white/5 bg-white/5 hover:border-white/10'}`}
>
Self-Paced
Learners go at their own speed.
setPacingMode('instructor_led')}
className={`flex-1 p-4 rounded-2xl border-2 transition-all text-left ${pacingMode === 'instructor_led' ? 'border-purple-500 bg-purple-500/10' : 'border-white/5 bg-white/5 hover:border-white/10'}`}
>
Instructor-Led
Cohort-based with specific dates.
{pacingMode === 'instructor_led' && (
)}
{/* Certificate Template Section */}
Design the HTML certificate that students will receive upon passing the course.
Available variables: {"{{student_name}}"}, {"{{course_title}}"}, {"{{date}}"}, {"{{score}}"}.
{/* Course Portability Section */}
Export Course
Download the entire course structure, modules, and lessons as a JSON file.
You can use this to backup or move content between organizations.
{exporting ? "Exporting..." : "Download JSON"}
);
}