"use client"
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
import {
faCalendarAlt,
faCheck,
faTimes,
faFileAlt,
faMoneyBillWave,
faSignature,
faCheckCircle,
faTimesCircle
} from '@fortawesome/free-solid-svg-icons';
import { useEffect, useState } from 'react';
import { getAccessToken } from '@/lib/auth';
type Semester = {
id: number | string;
semester: string;
direction: string;
quota: string;
note: string;
studentCom: string;
sum: string;
paid: string;
ukim: string;
createdOn: string;
dateChanged: string;
credits: string;
type: string;
doc: string;
doc1: string;
verified: string;
taxes: string;
signatures: string;
status: string;
completed: string;
};
type SemestersResponse = {
semesters: Semester[];
};
interface TableCellProps {
children: React.ReactNode;
className?: string;
}
const TableCell = ({ children, className = "" }: TableCellProps) => (
{children}
|
);
const StatusBadge = ({ status }: { status: string }) => {
const baseClasses = "px-2 py-1 rounded-full text-xs font-medium";
if (status === "валиден") {
return (
{status}
);
}
return (
{status}
);
};
const YesNoBadge = ({ value }: { value: string }) => {
if (value === "Да") {
return (
);
} else if (value === "Не") {
return (
);
}
return —;
};
const SignatureBadge = ({ signatures }: { signatures: string }) => {
const [completed, total] = signatures.split('/').map(Number);
const percentage = total > 0 ? (completed / total) * 100 : 0;
let colorClass = "text-red-600 bg-red-100";
if (percentage === 100) {
colorClass = "text-green-600 bg-green-100";
} else if (percentage >= 50) {
colorClass = "text-yellow-600 bg-yellow-100";
}
return (
{signatures}
);
};
export default function SemestersPage() {
const [semesters, setSemesters] = useState([]);
const [isLoading, setIsLoading] = useState(true);
const [errorMessage, setErrorMessage] = useState(null);
useEffect(() => {
let cancelled = false;
async function load() {
setIsLoading(true);
setErrorMessage(null);
const token = getAccessToken();
if (!token) {
setErrorMessage('Not authenticated. Please login again.');
setIsLoading(false);
return;
}
try {
const response = await fetch('https://iknow-api.onrender.com/api/user/getSemesters', {
method: 'GET',
headers: {
Authorization: `Bearer ${token}`,
},
});
if (!response.ok) {
const text = await response.text().catch(() => '');
throw new Error(text || `Failed to load semesters (${response.status})`);
}
const data = (await response.json()) as SemestersResponse;
if (!cancelled) setSemesters(Array.isArray(data?.semesters) ? data.semesters : []);
} catch (err) {
if (!cancelled) {
setErrorMessage(err instanceof Error ? err.message : 'Failed to load semesters.');
}
} finally {
if (!cancelled) setIsLoading(false);
}
}
void load();
return () => {
cancelled = true;
};
}, []);
if (isLoading) {
return (
);
}
if (errorMessage) {
return (
);
}
return (
{/* Header */}
Семестри
Преглед на сите запишани семестри и нивниот статус
{/* Table Container */}
Листа на семестри
| # |
Семестар |
Насока |
Квота |
Забелешка |
Студ.Ком. |
Сума |
Платено |
УКИМ |
Креирано на |
Датум промена |
Ц.Кр |
Тип |
Док. |
Док1. |
Вериф. |
Таксени |
Потписи |
Статус |
Зав. |
{semesters.map((semester) => (
{semester.id}
{semester.semester}
{semester.direction}
{semester.quota}
{semester.note ? (
{semester.note.length > 10 ? `${semester.note.substring(0, 10)}...` : semester.note}
) : (
—
)}
{semester.studentCom ? (
{semester.studentCom.length > 10 ? `${semester.studentCom.substring(0, 10)}...` : semester.studentCom}
) : (
—
)}
{semester.sum ? (
{semester.sum}
) : (
—
)}
{semester.paid ? (
{semester.paid}
) : (
—
)}
{semester.ukim ? (
{semester.ukim}
) : (
—
)}
{semester.createdOn}
{semester.dateChanged}
{semester.credits}
{semester.type}
{semester.taxes}
{semester.completed !== "Не" ? (
{semester.completed}
) : (
{semester.completed}
)}
))}
{/* Summary Cards */}
Завршени семестри
{semesters.filter(s => s.completed !== "Не").length}
Верифицирани
{semesters.filter(s => s.verified === "Да").length}
Вкупно семестри
{semesters.length}
);
}