<?php

namespace App\Controllers\Admin;

use App\Controllers\BaseController;
use App\Models\TeachingAssignmentModel;
use App\Models\TeacherModel;
use App\Models\ClassroomModel;
use App\Models\SchoolSubjectModel;
use App\Models\AcademicPeriodModel;
use App\Models\GradeModel;

class TeachingAssignment extends BaseController
{
    protected $teachingModel;
    protected $teacherModel;
    protected $classroomModel;
    protected $schoolSubjectModel;
    protected $periodModel;
    protected $gradeModel;

    public function __construct()
    {
        $this->teachingModel     = new TeachingAssignmentModel();
        $this->teacherModel      = new TeacherModel();
        $this->classroomModel    = new ClassroomModel();
        $this->schoolSubjectModel = new SchoolSubjectModel();
        $this->periodModel       = new AcademicPeriodModel();
        $this->gradeModel        = new GradeModel();
    }

    private function checkLogin()
    {
        if (!session()->get('logged_in')) {
            return redirect()->to('/login');
        }
        $role = session()->get('user_role');
        if (!in_array($role, ['superadmin', 'admin'])) {
            return redirect()->to('/dashboard')->with('error', 'Akses ditolak!');
        }
        return null;
    }

    public function index()
    {
        if ($redirect = $this->checkLogin()) return $redirect;

        $activePeriod = $this->periodModel->getActive();
        
        if (!$activePeriod) {
            return redirect()->to('/dashboard')
                ->with('error', 'Belum ada periode akademik aktif!');
        }

        // Ambil semua tingkat
        $grades = $this->gradeModel->orderBy('order', 'ASC')->findAll();
        
        // Ambil semua guru aktif untuk dropdown
        $teachers = $this->teacherModel->where('is_active', 1)
                                        ->orderBy('name', 'ASC')
                                        ->findAll();

        $data = [
            'title'         => 'Setting Mengajar (Guru Mapel)',
            'activePeriod'  => $activePeriod,
            'grades'        => $grades,
            'teachers'      => $teachers,
        ];

        return view('teaching_assignment/index', $data);
    }

    // AJAX: Ambil kelas berdasarkan tingkat
    public function getClassrooms()
    {
        if ($redirect = $this->checkLogin()) return $redirect;

        $gradeId = $this->request->getGet('grade_id');
        
        if (!$gradeId) {
            return $this->response->setJSON([]);
        }

        // Ambil tahun ajaran aktif
        $db = \Config\Database::connect();
        $activeYear = $db->table('academic_years')
                         ->where('is_active', 1)
                         ->where('deleted_at', null)
                         ->get()->getRowArray();

        $builder = $this->classroomModel
            ->select('classrooms.id, classrooms.name, grades.name as grade_name')
            ->join('grades', 'grades.id = classrooms.grade_id')
            ->where('classrooms.grade_id', $gradeId)
            ->where('classrooms.deleted_at', null);

        if ($activeYear) {
            $builder->where('classrooms.academic_year_id', $activeYear['id']);
        }

        $classrooms = $builder->orderBy('classrooms.name', 'ASC')->findAll();

        return $this->response->setJSON($classrooms);
    }

    // AJAX: Ambil mapel + assignment untuk kelas tertentu
    public function getSubjects()
    {
        if ($redirect = $this->checkLogin()) return $redirect;

        $classroomId = $this->request->getGet('classroom_id');
        $periodId    = $this->request->getGet('period_id');

        if (!$classroomId || !$periodId) {
            return $this->response->setJSON([]);
        }

        // Ambil mapel yang aktif dari school_subjects
        $subjects = $this->schoolSubjectModel->getActiveSubjects();
        
        // Urutkan mapel: Keagamaan → Umum → Tambahan
        $orderGroups = ['Keagamaan', 'Umum', 'Tambahan', 'Pilihan IPA', 'Pilihan IPS', 'Pilihan Lintas Minat'];
        usort($subjects, function($a, $b) use ($orderGroups) {
            $posA = array_search($a['group'] ?? 'Lainnya', $orderGroups);
            $posB = array_search($b['group'] ?? 'Lainnya', $orderGroups);
            if ($posA === false) $posA = 999;
            if ($posB === false) $posB = 999;
            return $posA - $posB;
        });
        
        // Ambil assignment yang sudah ada untuk kelas ini
        $assignments = $this->teachingModel->getMapByClassroom($classroomId, $periodId);
        
        // Ambil semua guru untuk dropdown
        $teachers = $this->teacherModel->where('is_active', 1)
                                        ->orderBy('name', 'ASC')
                                        ->findAll();

        return $this->response->setJSON([
            'subjects'    => $subjects,
            'assignments' => $assignments,
            'teachers'    => $teachers,
        ]);
    }

    // Simpan semua assignment
    public function save()
    {
        if ($redirect = $this->checkLogin()) return $redirect;

        $classroomId = $this->request->getPost('classroom_id');
        $periodId    = $this->request->getPost('period_id');
        $assignments = $this->request->getPost('assignments') ?? [];

        if (!$classroomId || !$periodId) {
            return $this->response->setJSON([
                'success' => false, 
                'message' => 'Data kelas atau periode tidak lengkap!'
            ]);
        }

        // Filter hanya yang memiliki teacher_id (tidak kosong)
        $filteredAssignments = [];
        foreach ($assignments as $subjectId => $teacherId) {
            if (!empty($teacherId)) {
                $filteredAssignments[$subjectId] = $teacherId;
            }
        }

        $classroom = $this->classroomModel->find($classroomId);
        if (!$classroom) {
            return $this->response->setJSON([
                'success' => false, 
                'message' => 'Kelas tidak ditemukan!'
            ]);
        }

        $success = $this->teachingModel->saveAssignments($classroomId, $periodId, $filteredAssignments);

        // KIRIM RESPONSE JSON
        return $this->response->setJSON([
            'success' => true, 
            'message' => "Berhasil menyimpan setting mengajar untuk kelas {$classroom['name']} ({$success} mapel)"
        ]);
    }

    public function syncFromAsc()
    {
        if ($redirect = $this->checkLogin()) return $redirect;

        $classroomId = $this->request->getGet('classroom_id');
        if (!$classroomId) {
            return $this->response->setJSON(['success' => false, 'message' => 'Kelas tidak valid!']);
        }

        // 1. Ambil import aSc yang aktif
        $ascImportModel = new \App\Models\AscImportModel();
        $activeImport = $ascImportModel->getActive();
        if (!$activeImport) {
            return $this->response->setJSON(['success' => false, 'message' => 'Belum ada jadwal aSc aktif yang dipublikasikan!']);
        }

        // 2. Cari pemetaan kelas ini di asc_classes
        $ascClassModel = new \App\Models\AscClassModel();
        $ascClass = $ascClassModel->where('import_id', $activeImport['id'])
                                  ->where('classroom_id', $classroomId)
                                  ->first();
        if (!$ascClass) {
            return $this->response->setJSON(['success' => false, 'message' => 'Kelas ini belum disinkronkan dengan kelas aSc oleh Admin!']);
        }

        // 3. Ambil semua penugasan unik untuk kelas ini di jadwal aSc
        $db = \Config\Database::connect();
        $rows = $db->table('asc_schedules')
            ->select('asc_subjects.school_subject_id, asc_teachers.teacher_id')
            ->join('asc_subjects', 'asc_subjects.asc_id = asc_schedules.subject_asc_id AND asc_subjects.import_id = asc_schedules.import_id')
            ->join('asc_teachers', 'asc_teachers.asc_id = asc_schedules.teacher_asc_id AND asc_teachers.import_id = asc_schedules.import_id')
            ->where('asc_schedules.import_id', $activeImport['id'])
            ->where('asc_schedules.class_asc_id', $ascClass['asc_id'])
            ->where('asc_teachers.teacher_id IS NOT NULL')
            ->where('asc_subjects.school_subject_id IS NOT NULL')
            ->groupBy(['asc_subjects.school_subject_id', 'asc_teachers.teacher_id'])
            ->get()
            ->getResultArray();

        $mappings = [];
        foreach ($rows as $row) {
            $mappings[$row['school_subject_id']] = $row['teacher_id'];
        }

        return $this->response->setJSON([
            'success' => true,
            'mappings' => $mappings,
            'message' => 'Berhasil memuat ' . count($mappings) . ' penugasan dari jadwal aSc. Silakan klik \'Simpan Semua\' untuk menyimpannya.'
        ]);
    }

    // AJAX: Ambil assignment dari Jadwal Otomatis (local schedule loads)
    public function syncFromLocal()
    {
        if ($redirect = $this->checkLogin()) return $redirect;

        $classroomId = $this->request->getGet('classroom_id');
        $activePeriod = $this->periodModel->getActive();
        
        if (!$classroomId || !$activePeriod) {
            return $this->response->setJSON(['success' => false, 'message' => 'Kelas atau periode tidak valid!']);
        }

        $db = \Config\Database::connect();
        
        // Ambil active academic year
        $activeYear = $db->table('academic_years')->where('is_active', 1)->get()->getRowArray();
        if (!$activeYear) {
            return $this->response->setJSON(['success' => false, 'message' => 'Tidak ada tahun ajaran aktif!']);
        }

        // Ambil semua beban kerja dari schedule_loads untuk kelas ini di periode ini
        $loads = $db->table('schedule_loads')
            ->select('school_subject_id, teacher_id')
            ->where('classroom_id', $classroomId)
            ->where('academic_year_id', $activeYear['id'])
            ->where('academic_period_id', $activePeriod['id'])
            ->get()
            ->getResultArray();

        $mappings = [];
        foreach ($loads as $load) {
            $mappings[(int)$load['school_subject_id']] = (int)$load['teacher_id'];
        }

        return $this->response->setJSON([
            'success' => true,
            'mappings' => $mappings,
            'message' => 'Berhasil memuat ' . count($mappings) . ' penugasan dari Jadwal Otomatis. Silakan klik \'Simpan Semua\' untuk menyimpannya.'
        ]);
    }

    // AJAX: Ambil assignment dari Jadwal Manual (manual schedule entries)
    public function syncFromManual()
    {
        if ($redirect = $this->checkLogin()) return $redirect;

        $classroomId = $this->request->getGet('classroom_id');
        $activePeriod = $this->periodModel->getActive();
        
        if (!$classroomId || !$activePeriod) {
            return $this->response->setJSON(['success' => false, 'message' => 'Kelas atau periode tidak valid!']);
        }

        $db = \Config\Database::connect();

        // 1. Ambil jadwal manual yang berstatus published (aktif) untuk periode akademik saat ini
        $publishedSchedule = $db->table('schedules')
            ->where('academic_period_id', $activePeriod['id'])
            ->where('type', 'manual')
            ->where('status', 'published')
            ->get()->getRowArray();

        if (!$publishedSchedule) {
            return $this->response->setJSON([
                'success' => false,
                'message' => 'Belum ada jadwal manual yang aktif (Terbit) untuk periode akademik saat ini.'
            ]);
        }

        // 2. Ambil semua penugasan unik dari schedule_entries untuk kelas ini
        $entries = $db->table('schedule_entries')
            ->select('school_subject_id, teacher_id')
            ->where('schedule_id', $publishedSchedule['id'])
            ->where('classroom_id', $classroomId)
            ->groupBy(['school_subject_id', 'teacher_id'])
            ->get()
            ->getResultArray();

        $mappings = [];
        foreach ($entries as $e) {
            if ($e['school_subject_id'] && $e['teacher_id']) {
                $mappings[(int)$e['school_subject_id']] = (int)$e['teacher_id'];
            }
        }

        return $this->response->setJSON([
            'success' => true,
            'mappings' => $mappings,
            'message' => 'Berhasil memuat ' . count($mappings) . ' penugasan dari Jadwal Manual ("' . $publishedSchedule['name'] . '"). Silakan klik \'Simpan Semua\' untuk menyimpannya.'
        ]);
    }
}