<?php

namespace App\Controllers\Guru;

use App\Controllers\BaseController;
use App\Models\SchoolSettingModel;
use App\Models\LearningDeviceModel;
use App\Models\LearningDeviceTpModel;
use App\Models\LearningDeviceProtaModel;
use App\Models\LearningDevicePromesModel;
use App\Models\LearningDeviceModulModel;
use App\Models\LearningDeviceKktpModel;
use App\Models\LearningDevicePekanEfektifModel;
use App\Controllers\Guru\Traits\DeviceHelperTrait;

class ExportController extends BaseController
{
    use DeviceHelperTrait;

    protected $deviceModel;
    protected $deviceTpModel;
    protected $protaModel;
    protected $promesModel;
    protected $modulModel;
    protected $kktpModel;
    protected $pekanEfektifModel;

    public function __construct()
    {
        $this->deviceModel       = new LearningDeviceModel();
        $this->deviceTpModel     = new LearningDeviceTpModel();
        $this->protaModel        = new LearningDeviceProtaModel();
        $this->promesModel       = new LearningDevicePromesModel();
        $this->modulModel        = new LearningDeviceModulModel();
        $this->kktpModel         = new LearningDeviceKktpModel();
        $this->pekanEfektifModel = new LearningDevicePekanEfektifModel();
    }

    /**
     * GET: Ekspor dokumen dalam format DOCX/PDF/ZIP
     */
    public function export($id, $format)
    {
        if ($redirect = $this->checkLogin()) return $redirect;

        $teacher = $this->getTeacher();
        $device = $this->deviceModel->getDetail($id, $teacher['user_id']);
        if (!$device) {
            return redirect()->to('/guru/learning-devices')->with('error', 'Dokumen tidak ditemukan.');
        }

        $device['teacher_name'] = $teacher['name'] ?? '';
        $device['teacher_nip'] = $teacher['nip'] ?? '';

        $exportService = new \App\Services\DocumentExportService();

        // 1. Ekspor Paket ZIP
        if ($format === 'package-zip') {
            try {
                $fileContent = $exportService->exportPackageZip($id, $device);
                return $this->response->setStatusCode(200)
                    ->setContentType('application/zip')
                    ->setHeader('Content-Disposition', 'attachment; filename="Paket_Perangkat_' . $id . '.zip"')
                    ->setBody($fileContent);
            } catch (\Throwable $e) {
                return redirect()->to('/guru/learning-devices/rpm/' . $id)
                    ->with('error', 'Gagal membuat paket ZIP: ' . $e->getMessage());
            }
        }

        // 2. Ekspor Modul Ajar Spesifik
        if (str_starts_with($format, 'modul-')) {
            $parts = explode('-', $format);
            $tpId = intval($parts[1]);
            $ext = $parts[2] ?? 'pdf';

            $modul = $this->modulModel->where('learning_device_id', $id)->where('tp_id', $tpId)->first();
            if (!$modul) {
                return redirect()->to('/guru/learning-devices/rpm/' . $id)->with('error', 'Modul Ajar belum digenerate.');
            }

            if ($ext === 'docx') {
                $tpCode = $modul['topic'] ? substr($modul['topic'], 0, 15) : 'Modul';
                $tpCodeClean = preg_replace('/[^a-zA-Z0-9_]/', '_', $tpCode);

                $chapters = json_decode($device['chapters'] ?? '[]', true) ?: [];
                $chapterIndex = intval($modul['chapter_index'] ?? 0);
                $chapterName = $chapters[$chapterIndex] ?? 'Materi Pokok';

                $tps = $this->deviceTpModel->getByDevice($id);
                $chapterTps = array_values(array_filter($tps, function ($tp) use ($chapterName) {
                    return ($tp['chapter'] ?? '') === $chapterName;
                }));
                if (empty($chapterTps)) {
                    $chapterTps = $tps;
                }

                $totalJp = 0;
                foreach ($chapterTps as $tp) $totalJp += (int) ($tp['allocated_hours'] ?? 0);

                // count meetings
                $promes = $this->promesModel->getPromesData($id);
                $promesMap = [];
                foreach ($promes as $pr) {
                    $promesMap[$pr['tp_id']][$pr['month']][$pr['week_number']] = $pr['allocated_hours'];
                }
                $totHours = 0;
                foreach ($chapterTps as $tp) {
                    $tpIdTmp = $tp['id'];
                    if (isset($promesMap[$tpIdTmp])) {
                        foreach ($promesMap[$tpIdTmp] as $mNum => $weeks) {
                            foreach ($weeks as $w => $hours) {
                                $totHours += intval($hours);
                            }
                        }
                    }
                }
                $jumlahPertemuan = max(1, (int)ceil($totHours / 4));

                $cpElementsDisplay = '';
                $cpElements = json_decode($device['cp_elements'] ?? '[]', true);
                $chapterCpMap = json_decode($device['chapter_cp_map'] ?? '{}', true);
                $selectedCpElement = $chapterCpMap[$chapterIndex] ?? '';
                if (!empty($selectedCpElement)) {
                    $cpElementsDisplay = is_array($selectedCpElement) ? implode(', ', $selectedCpElement) : $selectedCpElement;
                } elseif (is_array($cpElements)) {
                    $names = array_column($cpElements, 'name');
                    $cpElementsDisplay = implode(', ', $names);
                }

                $chapterDplMap = json_decode($device['chapter_dpl'] ?? '{}', true) ?: [];
                $chapterKbcMap = json_decode($device['chapter_kbc'] ?? '{}', true) ?: [];
                $dplChapterDisplay = implode(', ', $chapterDplMap[$chapterIndex] ?? []);
                $kbcChapterDisplay = implode(', ', $chapterKbcMap[$chapterIndex] ?? []);
                if (empty($dplChapterDisplay)) {
                    $dplArr = json_decode($device['dpl'] ?? '[]', true) ?: [];
                    $dplChapterDisplay = implode(', ', $dplArr);
                }
                if (empty($kbcChapterDisplay)) {
                    $kbcArr = json_decode($device['panca_cinta'] ?? '[]', true) ?: [];
                    $kbcChapterDisplay = implode(', ', $kbcArr);
                }

                $skenario = [];
                if (!empty($modul['skenario_pembelajaran'])) {
                    $skenario = is_string($modul['skenario_pembelajaran'])
                        ? json_decode($modul['skenario_pembelajaran'], true) ?? []
                        : $modul['skenario_pembelajaran'];
                }

                $daftarPustaka = $modul['daftar_pustaka'] ?? '';
                if (empty($daftarPustaka)) {
                    $daftarPustaka = "Kementerian Pendidikan, Kebudayaan, Riset, dan Teknologi. Buku Panduan Guru dan Buku Siswa " . ($device['subject_name'] ?? 'Mata Pelajaran') . " Kelas " . ($device['grade_name'] ?? '-') . ". Jakarta.";
                }

                $exportData = [
                    'device'       => $device,
                    'settings'     => $this->settingModel->getSettings() ?? [],
                    'modul'        => $modul,
                    'chapterName'  => $chapterName,
                    'chapterTps'   => $chapterTps,
                    'totalJp'      => $totalJp,
                    'jumlahPertemuan' => $jumlahPertemuan,
                    'cpElementsDisplay' => $cpElementsDisplay,
                    'dplChapterDisplay' => $dplChapterDisplay,
                    'kbcChapterDisplay' => $kbcChapterDisplay,
                    'daftarPustaka' => $daftarPustaka,
                    'skenario'     => $skenario,
                ];

                $fileContent = $exportService->exportModulBaru($exportData);
                return $this->response->setStatusCode(200)
                    ->setContentType('application/vnd.openxmlformats-officedocument.wordprocessingml.document')
                    ->setHeader('Content-Disposition', 'attachment; filename="Modul_Ajar_' . $tpCodeClean . '.docx"')
                    ->setBody($fileContent);
            } else {
                $fileContent = $exportService->exportPdf($device, 'modul', ['modul' => $modul]);
                return $this->response->setStatusCode(200)
                    ->setContentType('application/pdf')
                    ->setHeader('Content-Disposition', 'attachment; filename="Modul_Ajar_' . $tpId . '.pdf"')
                    ->setBody($fileContent);
            }
        }

        $tps = $this->deviceTpModel->getByDevice($id);
        $prota = $this->protaModel->getDetailedProta($id);
        $promes = $this->promesModel->getPromesData($id);

        $protaMap = [];
        foreach ($prota as $p) {
            $protaMap[$p['tp_id']] = $p;
        }
        $promesMap = [];
        foreach ($promes as $pr) {
            $promesMap[$pr['tp_id']][$pr['month']][$pr['week_number']] = $pr['allocated_hours'];
        }

        $rpeRecord = $this->pekanEfektifModel->where('learning_device_id', $id)->first();
        if ($rpeRecord) {
            $rpeData = json_decode($rpeRecord['content_json'], true);
        } else {
            $rpeData = $this->calculateRpeFromKaldik($id);
        }

        $promesData = ['tps' => $tps, 'promesMap' => $promesMap, 'protaMap' => $protaMap, 'rpeData' => $rpeData];

        // KKTP Export
        if ($format === 'kktp-docx' || $format === 'kktp-pdf') {
            $kktpsData = $this->kktpModel->getByDevice($id);
            $intervalsJson = $device['kktp_intervals'] ?? '';
            $intervals = json_decode($intervalsJson, true) ?: ['bimbingan' => 59, 'cukup' => 69, 'baik' => 84];
            $exportData = ['kktps' => $kktpsData, 'intervals' => $intervals];

            $ext = ($format === 'kktp-docx') ? 'docx' : 'pdf';
            $method = ($format === 'kktp-docx') ? 'exportDocx' : 'exportPdf';
            $fileContent = $exportService->{$method}($device, 'kktp', $exportData);

            return $this->response->setStatusCode(200)
                ->setContentType($ext === 'docx' ? 'application/vnd.openxmlformats-officedocument.wordprocessingml.document' : 'application/pdf')
                ->setHeader('Content-Disposition', 'attachment; filename="KKTP_' . $id . '.' . $ext . '"')
                ->setBody($fileContent);
        }

        // ATP Export Override
        if ($format === 'atp-docx') {
            $chapters = json_decode($device['chapters'] ?? '[]', true) ?: [];
            $chapterDplMap = json_decode($device['chapter_dpl'] ?? '{}', true) ?: [];
            $chapterKbcMap = json_decode($device['chapter_kbc'] ?? '{}', true) ?: [];
            $schoolSettingModel = new \App\Models\SchoolSettingModel();
            $settings = $schoolSettingModel->getSettings();
            $fileContent = $exportService->exportAtpWord($device, $tps, $chapters, $chapterDplMap, $chapterKbcMap, $settings);

            return $this->response->setStatusCode(200)
                ->setContentType('application/vnd.openxmlformats-officedocument.wordprocessingml.document')
                ->setHeader('Content-Disposition', 'attachment; filename="ATP_' . $device['subject_name'] . '_Kelas_' . $device['grade_name'] . '.docx"')
                ->setBody($fileContent);
        }

        $exportRoutes = [
            'atp-docx'      => ['method' => 'exportDocx', 'type' => 'atp', 'params' => ['tps' => $tps], 'ext' => 'docx', 'prefix' => 'ATP_'],
            'atp-pdf'       => ['method' => 'exportPdf', 'type' => 'atp', 'params' => ['tps' => $tps], 'ext' => 'pdf', 'prefix' => 'ATP_'],
            'prota-docx'    => ['method' => 'exportDocx', 'type' => 'prota', 'params' => ['prota' => $prota], 'ext' => 'docx', 'prefix' => 'PROTA_'],
            'prota-pdf'     => ['method' => 'exportPdf', 'type' => 'prota', 'params' => ['prota' => $prota], 'ext' => 'pdf', 'prefix' => 'PROTA_'],
            'promes-docx'   => ['method' => 'exportDocx', 'type' => 'promes', 'params' => $promesData, 'ext' => 'docx', 'prefix' => 'PROMES_'],
            'promes-pdf'    => ['method' => 'exportPdf', 'type' => 'promes', 'params' => $promesData, 'ext' => 'pdf', 'prefix' => 'PROMES_'],
            'rpe-docx'      => ['method' => 'exportDocx', 'type' => 'rpe', 'params' => ['rpeData' => $rpeData], 'ext' => 'docx', 'prefix' => 'RPE_'],
            'rpe-pdf'       => ['method' => 'exportPdf', 'type' => 'rpe', 'params' => ['rpeData' => $rpeData], 'ext' => 'pdf', 'prefix' => 'RPE_'],
        ];

        if (isset($exportRoutes[$format])) {
            $route = $exportRoutes[$format];
            $fileContent = $exportService->{$route['method']}($device, $route['type'], $route['params']);
            return $this->response->setStatusCode(200)
                ->setContentType($route['ext'] === 'docx' ? 'application/vnd.openxmlformats-officedocument.wordprocessingml.document' : 'application/pdf')
                ->setHeader('Content-Disposition', 'attachment; filename="' . $route['prefix'] . $device['subject_name'] . '_Kelas_' . $device['grade_name'] . '.' . $route['ext'] . '"')
                ->setBody($fileContent);
        }

        return redirect()->to('/guru/learning-devices')->with('error', 'Format ekspor tidak didukung.');
    }
}
