<?php

namespace App\Http\Controllers\Siswa;

use App\Http\Controllers\Controller;
use App\Models\Badge;
use App\Models\PengumpulanTugas;
use App\Models\SiswaBadge;
use App\Services\BadgeService;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Storage;
use Carbon\Carbon;
use App\Models\Tugas;

class TugasController extends Controller
{
    public function __construct()
    {
        $this->middleware('auth:siswa');
    }

    public function index()
    {
        $siswa = Auth::guard('siswa')->user();

        $semuaTugas = Tugas::with(['mengajar.mapel', 'mengajar.guru'])
            ->whereHas('mengajar', function ($q) use ($siswa) {
                $q->where('id_kelas', $siswa->id_kelas);
            })
            ->orderBy('deadline', 'asc')
            ->get();

        $now = Carbon::now();

        $tugasList = $semuaTugas->map(function ($tugas) use ($siswa, $now) {
            $pengumpulan = PengumpulanTugas::where('id_tugas', $tugas->id_tugas)
                ->where('id_siswa', $siswa->id_siswa)
                ->first();

            $deadline = Carbon::parse($tugas->deadline);

            if ($pengumpulan && $pengumpulan->lampiran_tugas !== null) {
                $status      = $pengumpulan->tanggal_submit && Carbon::parse($pengumpulan->tanggal_submit)->lessThanOrEqualTo($deadline)
                    ? 'dikumpulkan'
                    : 'terlambat';
                $sudahKumpul = true;
            } else {
                $status      = $now->greaterThan($deadline) ? 'terlambat' : 'belum';
                $sudahKumpul = false;
            }

            return [
                'id_tugas'     => $tugas->id_tugas,
                'judul'        => $tugas->judul_tugas,
                'keterangan'   => $tugas->keterangan,
                'deadline'     => $deadline,
                'nama_mapel'   => optional(optional($tugas->mengajar)->mapel)->nama_mapel ?? '-',
                'nama_guru'    => optional(optional($tugas->mengajar)->guru)->nama ?? '-',
                'status'       => $status,
                'sudah_kumpul' => $sudahKumpul,
                'lampiran'     => $pengumpulan?->lampiran_tugas,
                'exp'          => $pengumpulan?->exp ?? 0,
                'file_tugas'   => $tugas->lampiran,
            ];
        });

        $tugasBelum     = $tugasList->filter(fn($t) => !$t['sudah_kumpul'] && $t['status'] !== 'terlambat');
        $tugasTerlambat = $tugasList->filter(fn($t) => !$t['sudah_kumpul'] && $t['status'] === 'terlambat');
        $tugasSelesai   = $tugasList->filter(fn($t) => $t['sudah_kumpul']);

        return view('siswa.tugas.index', compact('tugasBelum', 'tugasTerlambat', 'tugasSelesai'));
    }

    public function show($id_tugas)
    {
        $siswa = Auth::guard('siswa')->user();

        $tugas = Tugas::with(['mengajar.mapel', 'mengajar.guru'])
            ->whereHas('mengajar', function ($q) use ($siswa) {
                $q->where('id_kelas', $siswa->id_kelas);
            })
            ->where('id_tugas', $id_tugas)
            ->firstOrFail();

        $pengumpulan = PengumpulanTugas::where('id_tugas', $id_tugas)
            ->where('id_siswa', $siswa->id_siswa)
            ->first();

        $sudahKumpul = $pengumpulan && $pengumpulan->lampiran_tugas !== null;
        $terlambat   = Carbon::now()->greaterThan(Carbon::parse($tugas->deadline));

        return view('siswa.tugas.show', compact('tugas', 'pengumpulan', 'sudahKumpul', 'terlambat'));
    }

    /**
     * Submit tugas.
     *
     * EXP tidak lagi diupdate ke leaderboard di sini.
     * EXP dihitung dinamis di LeaderboardController::hitungExpSiswa()
     * berdasarkan tanggal_submit vs deadline secara real-time.
     */
    public function submit(Request $request, $id_tugas)
    {
        $siswa = Auth::guard('siswa')->user();

        $request->validate([
            'lampiran_tugas' => 'required|file|mimes:pdf,doc,docx,jpg,jpeg,png|max:5120',
        ], [
            'lampiran_tugas.required' => 'File jawaban wajib diupload.',
            'lampiran_tugas.mimes'    => 'Format file harus pdf, doc, docx, jpg, atau png.',
            'lampiran_tugas.max'      => 'Ukuran file maksimal 5MB.',
        ]);

        $tugas = Tugas::whereHas('mengajar', function ($q) use ($siswa) {
                $q->where('id_kelas', $siswa->id_kelas);
            })
            ->where('id_tugas', $id_tugas)
            ->firstOrFail();

        $sudahAda = PengumpulanTugas::where('id_tugas', $id_tugas)
            ->where('id_siswa', $siswa->id_siswa)
            ->whereNotNull('lampiran_tugas')
            ->exists();

        if ($sudahAda) {
            return back()->with('error', 'Kamu sudah mengumpulkan tugas ini.');
        }

        $file     = $request->file('lampiran_tugas');
        $filename = 'tugas_' . $siswa->id_siswa . '_' . $id_tugas . '_' . time() . '.' . $file->getClientOriginalExtension();
        $path     = $file->storeAs('pengumpulan_tugas', $filename, 'public');

        $now       = Carbon::now();
        $deadline  = Carbon::parse($tugas->deadline);
        $terlambat = $now->greaterThan($deadline);
        $status    = $terlambat ? 'terlambat' : 'dikumpulkan';

        PengumpulanTugas::updateOrCreate(
            ['id_tugas' => $id_tugas, 'id_siswa' => $siswa->id_siswa],
            [
                'lampiran_tugas' => $path,
                'tanggal_submit' => $now,
                'exp'            => $terlambat ? -5 : 10, // catatan saja, tidak dipakai di leaderboard
                'status'         => $status,
            ]
        );

        if (!$terlambat) {
            $badgeSebelum = SiswaBadge::where('id_siswa', $siswa->id_siswa)->pluck('id_badge')->toArray();
            app(BadgeService::class)->checkTugasBadges($siswa->id_siswa);
            $badgeSesudah = SiswaBadge::where('id_siswa', $siswa->id_siswa)->pluck('id_badge')->toArray();
            $idBadgeBaru  = array_diff($badgeSesudah, $badgeSebelum);
            if (!empty($idBadgeBaru)) {
                session()->flash('badge_baru', Badge::whereIn('id_badge', $idBadgeBaru)->get());
            }
        }

        $pesan = $terlambat
            ? 'Tugas berhasil dikumpulkan (terlambat). Kamu mendapat penalti -5 poin. 😔'
            : 'Tugas berhasil dikumpulkan! Kamu mendapat +10 poin! 🎉';

        return redirect()->route('siswa.tugas.index')->with('success', $pesan);
    }

    public function gantiFile(Request $request, $id_tugas)
    {
        $siswa = Auth::guard('siswa')->user();

        $request->validate([
            'lampiran_tugas' => 'required|file|mimes:pdf,doc,docx,jpg,jpeg,png|max:5120',
        ]);

        $tugas = Tugas::whereHas('mengajar', function ($q) use ($siswa) {
                $q->where('id_kelas', $siswa->id_kelas);
            })
            ->where('id_tugas', $id_tugas)
            ->firstOrFail();

        if (Carbon::now()->greaterThan(Carbon::parse($tugas->deadline))) {
            return back()->with('error_ganti', 'Deadline sudah lewat, file tidak dapat diganti.');
        }

        $pengumpulan = PengumpulanTugas::where('id_tugas', $id_tugas)
            ->where('id_siswa', $siswa->id_siswa)
            ->firstOrFail();

        if ($pengumpulan->lampiran_tugas) {
            Storage::disk('public')->delete($pengumpulan->lampiran_tugas);
        }

        $file     = $request->file('lampiran_tugas');
        $filename = 'tugas_' . $siswa->id_siswa . '_' . $id_tugas . '_' . time() . '.' . $file->getClientOriginalExtension();
        $path     = $file->storeAs('pengumpulan_tugas', $filename, 'public');

        $pengumpulan->update([
            'lampiran_tugas' => $path,
            'tanggal_submit' => Carbon::now(),
            'status'         => 'dikumpulkan',
            'exp'            => 10,
        ]);

        return back()->with('success', 'File jawaban berhasil diganti! ✅');
    }
}