diff --git a/app/Http/Controllers/Mahasiswa/LmsController.php b/app/Http/Controllers/Mahasiswa/LmsController.php index 91a4253..60df92e 100644 --- a/app/Http/Controllers/Mahasiswa/LmsController.php +++ b/app/Http/Controllers/Mahasiswa/LmsController.php @@ -4,34 +4,118 @@ use App\Http\Controllers\Controller; use App\Models\Kelas; +use App\Models\TahunAkademik; +use Illuminate\Http\Request; use Illuminate\Support\Facades\Auth; class LmsController extends Controller { /** * Show LMS dashboard with enrolled kelas + * Supports semester filtering: aktif, arsip, semua */ - public function index() + public function index(Request $request) { $mahasiswa = Auth::user()->mahasiswa; if (!$mahasiswa) { abort(403, 'Anda tidak memiliki akses sebagai mahasiswa.'); } - // Get enrolled kelas - $krs = $mahasiswa->krs()->where('status', 'approved')->first(); - $kelasIds = $krs?->krsDetail?->pluck('kelas_id')->toArray() ?? []; + // Get active tahun akademik + $tahunAktif = TahunAkademik::active(); + + // Get all approved KRS with kelas data + $allKrs = $mahasiswa->krs() + ->where('status', 'approved') + ->with(['tahunAkademik', 'krsDetail.kelas.mataKuliah', 'krsDetail.kelas.dosen.user', 'krsDetail.kelas.tahunAkademik']) + ->get(); - $kelasList = Kelas::whereIn('id', $kelasIds) - ->with(['mataKuliah', 'dosen.user', 'tugas' => fn($q) => $q->where('is_active', true)]) - ->get() - ->map(function($kelas) use ($mahasiswa) { - // Count pending tugas (not submitted yet) - $submittedTugasIds = $mahasiswa->tugasSubmissions()->pluck('tugas_id')->toArray(); - $kelas->pending_tugas = $kelas->tugas->whereNotIn('id', $submittedTugasIds)->count(); + // Extract all kelas from KRS details with the KRS tahun_akademik for proper filtering + $allKelas = $allKrs->flatMap(function($krs) { + return $krs->krsDetail->map(function($detail) use ($krs) { + $kelas = $detail->kelas; + $kelas->krs_tahun_akademik = $krs->tahunAkademik; + $kelas->krs_tahun_akademik_id = $krs->tahun_akademik_id; // Use this for filtering! return $kelas; }); + })->unique('id'); + + // Get available semesters for dropdown with sequential numbering + $semesterList = $allKrs->pluck('tahunAkademik')->unique('id')->sortBy('id'); // Sort chronologically (oldest first) + + // Add semester number (Semester 1, 2, 3...) based on enrollment order + $semesterNumber = 1; + $availableSemesters = $semesterList->map(function($semester) use (&$semesterNumber) { + $semester->semester_number = $semesterNumber; + $semester->semester_label = "Semester {$semesterNumber}"; + $semesterNumber++; + return $semester; + })->sortByDesc('id'); // Sort back to newest first for dropdown display + + // Get current semester number (for active semester) + $currentSemesterNumber = $tahunAktif ? $availableSemesters->firstWhere('id', $tahunAktif->id)?->semester_number : null; + + // Determine semester filter - USE krs_tahun_akademik_id for filtering (semester when enrolled) + if ($tahunAktif === null) { + // Libur semester: check if specific semester is selected + $semesterFilter = $request->query('semester', 'semua'); + + if (is_numeric($semesterFilter)) { + // Filter by specific semester (using KRS tahun akademik) + $kelasList = $allKelas->filter(fn($k) => $k->krs_tahun_akademik_id == $semesterFilter); + } else { + // Show all classes + $kelasList = $allKelas; + $semesterFilter = 'semua'; + } + } else { + $semesterFilter = $request->query('semester', 'aktif'); + + if (is_numeric($semesterFilter)) { + // Filter by specific semester ID (using KRS tahun akademik) + $kelasList = $allKelas->filter(fn($k) => $k->krs_tahun_akademik_id == $semesterFilter); + } elseif ($semesterFilter === 'aktif') { + // Show active semester classes (using KRS tahun akademik) + $kelasList = $allKelas->filter(fn($k) => $k->krs_tahun_akademik_id === $tahunAktif->id); + } else { + // Default to active + $kelasList = $allKelas->filter(fn($k) => $k->krs_tahun_akademik_id === $tahunAktif->id); + $semesterFilter = 'aktif'; + } + } + + // Add pending tugas count and archive status to each kelas + $kelasList = $kelasList->map(function($kelas) use ($mahasiswa, $tahunAktif) { + // Count pending tugas (only for active semester) + // Use krs_tahun_akademik_id to determine if archived (based on enrollment semester) + $isArchived = $tahunAktif === null || $kelas->krs_tahun_akademik_id !== $tahunAktif->id; + $kelas->is_archived = $isArchived; + + if (!$isArchived) { + $submittedTugasIds = $mahasiswa->tugasSubmissions()->pluck('tugas_id')->toArray(); + $activeTugas = $kelas->tugas()->where('is_active', true)->get(); + $kelas->pending_tugas = $activeTugas->whereNotIn('id', $submittedTugasIds)->count(); + } else { + $kelas->pending_tugas = 0; + } + + return $kelas; + }); + + // Group by semester for display (especially for 'semua' views) + // Use krs_tahun_akademik_id for proper grouping by enrollment semester + $kelasGrouped = $kelasList->groupBy(function($kelas) use ($availableSemesters) { + $semester = $availableSemesters->firstWhere('id', $kelas->krs_tahun_akademik_id); + return $semester?->semester_label ?? $kelas->krs_tahun_akademik->display_name ?? 'Unknown'; + }); - return view('mahasiswa.lms.index', compact('kelasList')); + return view('mahasiswa.lms.index', compact( + 'kelasList', + 'kelasGrouped', + 'semesterFilter', + 'availableSemesters', + 'tahunAktif', + 'currentSemesterNumber' + )); } } diff --git a/app/Http/Controllers/Mahasiswa/MateriController.php b/app/Http/Controllers/Mahasiswa/MateriController.php index 47621e0..444c060 100644 --- a/app/Http/Controllers/Mahasiswa/MateriController.php +++ b/app/Http/Controllers/Mahasiswa/MateriController.php @@ -6,6 +6,7 @@ use App\Models\Kelas; use App\Models\Materi; use App\Models\Pertemuan; +use App\Models\TahunAkademik; use Illuminate\Http\Request; use Illuminate\Support\Facades\Auth; use Illuminate\Support\Facades\Storage; @@ -14,6 +15,7 @@ class MateriController extends Controller { /** * Show materi for a specific kelas (mahasiswa view) + * Supports historical access for archived semesters */ public function index($kelasId) { @@ -22,7 +24,7 @@ public function index($kelasId) abort(403, 'Anda tidak memiliki akses sebagai mahasiswa.'); } - // Verify mahasiswa is enrolled in this kelas + // Verify mahasiswa is enrolled in this kelas (from any semester) $isEnrolled = $mahasiswa->krs() ->where('status', 'approved') ->whereHas('krsDetail', fn($q) => $q->where('kelas_id', $kelasId)) @@ -32,7 +34,11 @@ public function index($kelasId) abort(403, 'Anda tidak terdaftar di kelas ini.'); } - $kelas = Kelas::with('mataKuliah', 'dosen.user')->findOrFail($kelasId); + $kelas = Kelas::with('mataKuliah', 'dosen.user', 'tahunAkademik')->findOrFail($kelasId); + + // Check if this is an archived class + $tahunAktif = TahunAkademik::active(); + $isArchived = $tahunAktif === null || $kelas->tahun_akademik_id !== $tahunAktif->id; // Get all pertemuan for this kelas $pertemuanList = Pertemuan::whereHas('jadwalKuliah', fn($q) => $q->where('kelas_id', $kelasId)) @@ -40,7 +46,7 @@ public function index($kelasId) ->orderBy('pertemuan_ke') ->get(); - return view('mahasiswa.materi.index', compact('kelas', 'pertemuanList')); + return view('mahasiswa.materi.index', compact('kelas', 'pertemuanList', 'isArchived')); } /** diff --git a/app/Http/Controllers/Mahasiswa/TugasController.php b/app/Http/Controllers/Mahasiswa/TugasController.php index 832084f..3326aad 100644 --- a/app/Http/Controllers/Mahasiswa/TugasController.php +++ b/app/Http/Controllers/Mahasiswa/TugasController.php @@ -4,6 +4,7 @@ use App\Http\Controllers\Controller; use App\Models\Kelas; +use App\Models\TahunAkademik; use App\Models\Tugas; use App\Models\TugasSubmission; use Illuminate\Http\Request; @@ -14,12 +15,13 @@ class TugasController extends Controller { /** * List all tugas for a kelas + * Supports historical access for archived semesters */ public function index($kelasId) { $mahasiswa = Auth::user()->mahasiswa; - // Verify enrollment + // Verify enrollment (from any semester) $isEnrolled = $mahasiswa->krs() ->where('status', 'approved') ->whereHas('krsDetail', fn($q) => $q->where('kelas_id', $kelasId)) @@ -29,26 +31,35 @@ public function index($kelasId) abort(403, 'Anda tidak terdaftar di kelas ini.'); } - $kelas = Kelas::with(['mataKuliah', 'dosen.user'])->findOrFail($kelasId); + $kelas = Kelas::with(['mataKuliah', 'dosen.user', 'tahunAkademik'])->findOrFail($kelasId); + + // Check if this is an archived class + $tahunAktif = TahunAkademik::active(); + $isArchived = $tahunAktif === null || $kelas->tahun_akademik_id !== $tahunAktif->id; + + // Get tugas with submission status (show all tugas for archived, only active for current) + $tugasQuery = Tugas::where('kelas_id', $kelasId) + ->with(['submissions' => fn($q) => $q->where('mahasiswa_id', $mahasiswa->id)]); + + // For active semester, only show active tugas. For archived, show all. + if (!$isArchived) { + $tugasQuery->where('is_active', true); + } - // Get tugas with submission status - $tugasList = Tugas::where('kelas_id', $kelasId) - ->where('is_active', true) - ->with(['submissions' => fn($q) => $q->where('mahasiswa_id', $mahasiswa->id)]) - ->latest() - ->get(); - - return view('mahasiswa.tugas.index', compact('kelas', 'tugasList', 'mahasiswa')); + $tugasList = $tugasQuery->latest()->get(); + + return view('mahasiswa.tugas.index', compact('kelas', 'tugasList', 'mahasiswa', 'isArchived')); } /** * Show tugas detail + * Supports historical access for archived semesters */ public function show($kelasId, Tugas $tugas) { $mahasiswa = Auth::user()->mahasiswa; - // Verify enrollment + // Verify enrollment (from any semester) $isEnrolled = $mahasiswa->krs() ->where('status', 'approved') ->whereHas('krsDetail', fn($q) => $q->where('kelas_id', $kelasId)) @@ -58,10 +69,15 @@ public function show($kelasId, Tugas $tugas) abort(403); } - $kelas = Kelas::with(['mataKuliah', 'dosen.user'])->findOrFail($kelasId); + $kelas = Kelas::with(['mataKuliah', 'dosen.user', 'tahunAkademik'])->findOrFail($kelasId); + + // Check if this is an archived class + $tahunAktif = TahunAkademik::active(); + $isArchived = $tahunAktif === null || $kelas->tahun_akademik_id !== $tahunAktif->id; + $submission = $tugas->submissions()->where('mahasiswa_id', $mahasiswa->id)->first(); - return view('mahasiswa.tugas.show', compact('kelas', 'tugas', 'submission')); + return view('mahasiswa.tugas.show', compact('kelas', 'tugas', 'submission', 'isArchived')); } /** diff --git a/debug_output.txt b/debug_output.txt new file mode 100644 index 0000000..e131a73 --- /dev/null +++ b/debug_output.txt @@ -0,0 +1,47 @@ +Mahasiswa: Budi Santoso +ID: 1 + +=== KRS Records === +KRS #1 - TahunAkademik ID: 4 - 2022/2023 Ganjil + KRS Detail Count: 7 + - Kelas ID: 1, Kelas Tahun: 3 + - Kelas ID: 2, Kelas Tahun: 3 + - Kelas ID: 3, Kelas Tahun: 3 + - Kelas ID: 4, Kelas Tahun: 3 + - Kelas ID: 5, Kelas Tahun: 3 + - Kelas ID: 6, Kelas Tahun: 3 + - Kelas ID: 7, Kelas Tahun: 3 +KRS #2 - TahunAkademik ID: 5 - 2022/2023 Genap + KRS Detail Count: 7 + - Kelas ID: 8, Kelas Tahun: 3 + - Kelas ID: 9, Kelas Tahun: 3 + - Kelas ID: 10, Kelas Tahun: 3 + - Kelas ID: 11, Kelas Tahun: 3 + - Kelas ID: 12, Kelas Tahun: 3 + - Kelas ID: 13, Kelas Tahun: 3 + - Kelas ID: 14, Kelas Tahun: 3 +KRS #3 - TahunAkademik ID: 1 - 2023/2024 Ganjil + KRS Detail Count: 7 + - Kelas ID: 15, Kelas Tahun: 1 + - Kelas ID: 16, Kelas Tahun: 1 + - Kelas ID: 17, Kelas Tahun: 1 + - Kelas ID: 18, Kelas Tahun: 1 + - Kelas ID: 19, Kelas Tahun: 1 + - Kelas ID: 20, Kelas Tahun: 1 + - Kelas ID: 21, Kelas Tahun: 1 +KRS #4 - TahunAkademik ID: 2 - 2023/2024 Genap + KRS Detail Count: 7 + - Kelas ID: 22, Kelas Tahun: 2 + - Kelas ID: 23, Kelas Tahun: 2 + - Kelas ID: 24, Kelas Tahun: 2 + - Kelas ID: 25, Kelas Tahun: 2 + - Kelas ID: 26, Kelas Tahun: 2 + - Kelas ID: 27, Kelas Tahun: 2 + - Kelas ID: 28, Kelas Tahun: 2 + +=== Tahun Akademik === +ID: 1 - 2023/2024 Ganjil - Active: No +ID: 2 - 2023/2024 Genap - Active: No +ID: 3 - 2024/2025 Ganjil - Active: Yes +ID: 4 - 2022/2023 Ganjil - Active: No +ID: 5 - 2022/2023 Genap - Active: No diff --git a/debug_semester.php b/debug_semester.php new file mode 100644 index 0000000..85c01ee --- /dev/null +++ b/debug_semester.php @@ -0,0 +1,41 @@ +make('Illuminate\Contracts\Console\Kernel')->bootstrap(); + +use App\Models\Mahasiswa; +use App\Models\TahunAkademik; + +$output = ""; + +// Get first mahasiswa +$mahasiswa = Mahasiswa::first(); +$output .= "Mahasiswa: " . ($mahasiswa->user->name ?? 'Unknown') . "\n"; +$output .= "ID: " . $mahasiswa->id . "\n\n"; + +// Get all approved KRS +$allKrs = $mahasiswa->krs() + ->where('status', 'approved') + ->with(['tahunAkademik', 'krsDetail.kelas']) + ->get(); + +$output .= "=== KRS Records ===\n"; +foreach ($allKrs as $krs) { + $output .= "KRS #{$krs->id} - TahunAkademik ID: {$krs->tahun_akademik_id} - {$krs->tahunAkademik->display_name}\n"; + $output .= " KRS Detail Count: " . $krs->krsDetail->count() . "\n"; + foreach ($krs->krsDetail as $detail) { + $kelas = $detail->kelas; + $output .= " - Kelas ID: {$detail->kelas_id}, Kelas Tahun: " . ($kelas->tahun_akademik_id ?? 'null') . "\n"; + } +} + +$output .= "\n=== Tahun Akademik ===\n"; +$tahunAkademiks = TahunAkademik::orderBy('id')->get(); +foreach ($tahunAkademiks as $ta) { + $output .= "ID: {$ta->id} - {$ta->display_name} - Active: " . ($ta->is_active ? 'Yes' : 'No') . "\n"; +} + +file_put_contents('debug_output.txt', $output); +echo "Output written to debug_output.txt\n"; diff --git a/resources/views/mahasiswa/lms/_kelas-card.blade.php b/resources/views/mahasiswa/lms/_kelas-card.blade.php new file mode 100644 index 0000000..c119d02 --- /dev/null +++ b/resources/views/mahasiswa/lms/_kelas-card.blade.php @@ -0,0 +1,43 @@ +{{-- Kelas Card Partial - reusable card component for kelas list --}} +
{{ $kelas->mataKuliah->kode_mk }} • {{ $kelas->mataKuliah->sks }} SKS
++ Dosen: {{ $kelas->dosen->user->name ?? '-' }} +
+ + @if(($kelas->pending_tugas ?? 0) > 0 && !($kelas->is_archived ?? false)) ++ + {{ $kelas->pending_tugas }} tugas belum dikumpulkan +
+Akses materi dan tugas dari kelas yang Anda ambil
+ @if($tahunAktif !== null) + +Semua kelas bersifat read-only.
+Tidak ada kelas pada semester ini.
+ ← Kembali ke Semester Aktif + @elseAnda belum terdaftar di kelas apapun.
Isi KRS → + @endif +{{ $kelas->mataKuliah->kode_mk }} • {{ $kelas->mataKuliah->sks }} SKS
-- Dosen: {{ $kelas->dosen->user->name ?? '-' }} -
- - @if($kelas->pending_tugas > 0) -- - {{ $kelas->pending_tugas }} tugas belum dikumpulkan -
-{{ $kelas->mataKuliah->kode_mk }} • {{ $kelas->mataKuliah->sks }} SKS • Dosen: {{ $kelas->dosen->user->name ?? '-' }}
{{ $kelas->mataKuliah->kode_mk }} • Dosen: {{ $kelas->dosen->user->name ?? '-' }}
{{ $kelas->mataKuliah->nama_mk }} - {{ $kelas->nama_kelas }}
@if($tugas->deskripsi) @@ -69,6 +84,14 @@Menunggu penilaian dari dosen...
@endifArsip Semester
+Tugas ini dari semester sebelumnya. Pengumpulan tidak tersedia.
+