<?php
// api/kemandirian.php
// Fitur 3: Potensi Kemandirian Warga
// Hitung skor kemandirian berdasarkan: penghasilan, status kerja anggota, jumlah tanggungan
// Method: GET (list/detail/statistik), POST (catat perkembangan manual), PUT (set exit plan)

header('Content-Type: application/json');
header('Access-Control-Allow-Origin: *');
header('Access-Control-Allow-Methods: GET, POST, PUT, OPTIONS');
header('Access-Control-Allow-Headers: Content-Type');

if ($_SERVER['REQUEST_METHOD'] === 'OPTIONS') { http_response_code(200); exit; }

require_once '../config/db.php';
require_once 'middleware.php';

/* ─────────────────────────────────────────────
   HELPER
───────────────────────────────────────────── */
function getKonfig(PDO $pdo, string $kunci, $default = null) {
    $stmt = $pdo->prepare("SELECT nilai, tipe FROM konfigurasi_sistem WHERE kunci = ?");
    $stmt->execute([$kunci]);
    $row = $stmt->fetch(PDO::FETCH_ASSOC);
    if (!$row) return $default;
    return match($row['tipe']) {
        'integer' => (int)$row['nilai'],
        'decimal' => (float)$row['nilai'],
        'boolean' => filter_var($row['nilai'], FILTER_VALIDATE_BOOLEAN),
        default   => $row['nilai'],
    };
}

function hitungUsia(?string $tanggalLahir): ?int {
    if (!$tanggalLahir) return null;
    $lahir = new DateTime($tanggalLahir);
    $today = new DateTime();
    return (int)$today->diff($lahir)->y;
}

/* ─────────────────────────────────────────────
   CORE: Hitung Skor Kemandirian
   
   Komponen:
   A) Skor Penghasilan (bobot configurable, default 40%)
      - 0%  : penghasilan = 0
      - 50% : penghasilan = 50% threshold
      - 100%: penghasilan >= threshold UMR
   
   B) Skor Status Kerja (default 35%)
      - Dihitung dari anggota usia produktif (18-55)
      - Poin per anggota: bekerja_tetap=100, tidak_tetap=60, tidak_bekerja=0, pelajar=30
      - Bonus: sudah bekerja tetap setelah ikut pelatihan
   
   C) Skor Tanggungan (default 25%)  
      - Tanggungan sedikit (1-2) = skor tinggi
      - Tanggungan banyak (> 6) = skor rendah
      
   Status kemandirian:
   - 0-20  : sangat_bergantung
   - 21-40 : bergantung
   - 41-60 : berkembang
   - 61-79 : berpotensi_mandiri
   - 80+   : mandiri (siap exit)
───────────────────────────────────────────── */
function hitungSkorKemandirian(
    PDO $pdo,
    array $warga,
    array $anggotaList,
    float $thresholdPenghasilan,
    int $bobotPenghasilan,
    int $bobotStatusKerja,
    int $bobotTanggungan
): array {
    $penghasilan  = (float)$warga['penghasilan_bulanan'];
    $tanggungan   = (int)$warga['jumlah_tanggungan'];
    $statusKerja  = $warga['status_pekerjaan'];

    /* ── A: Skor Penghasilan ── */
    $skorPenghasilan = 0;
    if ($thresholdPenghasilan > 0) {
        $skorPenghasilan = (int)min(100, round($penghasilan / $thresholdPenghasilan * 100));
    }

    /* ── B: Skor Status Kerja ── */
    $bobotStatusKerjaMap = [
        'tetap'        => 100,
        'tidak_tetap'  => 60,
        'pensiun'      => 50,
        'tidak_bekerja'=> 0,
    ];

    // Skor kepala keluarga
    $poinKK      = $bobotStatusKerjaMap[$statusKerja] ?? 0;
    $anggotaProd = array_filter($anggotaList, function($a) {
        $usia = hitungUsia($a['tanggal_lahir']);
        return $usia !== null && $usia >= 18 && $usia <= 55;
    });

    if (count($anggotaProd) > 0) {
        $totalPoin = $poinKK;
        foreach ($anggotaProd as $a) {
            $stsBekMap = [
                'bekerja'       => 100,
                'pensiunan'     => 50,
                'pelajar'       => 30,
                'tidak_bekerja' => 0,
            ];
            $poin = $stsBekMap[$a['status_bekerja']] ?? 0;
            // Diskon: tidak bisa bekerja / disabilitas
            if (!$a['dapat_bekerja'] || in_array($a['kondisi_kesehatan'], ['sakit_berat','disabilitas'])) {
                $poin = (int)($poin * 0.3);
            }
            $totalPoin += $poin;
        }
        $jumlahDitimbang = count($anggotaProd) + 1; // +1 untuk KK
        $skorStatusKerja = (int)round($totalPoin / ($jumlahDitimbang * 100) * 100);
    } else {
        // Tidak ada anggota produktif, skor bergantung murni dari KK
        $skorStatusKerja = $poinKK;
    }

    /* ── C: Skor Tanggungan ── */
    // Makin sedikit tanggungan relatif terhadap yang bekerja = makin mandiri
    $anggotaBekerja = count(array_filter($anggotaList, fn($a) => $a['status_bekerja'] === 'bekerja'));
    $pencariNafkah  = $anggotaBekerja + ($statusKerja !== 'tidak_bekerja' ? 1 : 0);

    if ($tanggungan <= 0) {
        $skorTanggungan = 100;
    } elseif ($pencariNafkah >= $tanggungan) {
        $skorTanggungan = 100; // semua tanggungan punya pemasukan
    } else {
        $rasio           = $pencariNafkah / $tanggungan;
        $skorTanggungan  = (int)min(100, round($rasio * 100));
    }

    /* ── Skor Total (weighted) ── */
    $totalBobot  = $bobotPenghasilan + $bobotStatusKerja + $bobotTanggungan;
    if ($totalBobot <= 0) $totalBobot = 100;

    $skorTotal = (int)round(
        ($skorPenghasilan * $bobotPenghasilan
       + $skorStatusKerja * $bobotStatusKerja
       + $skorTanggungan  * $bobotTanggungan) / $totalBobot
    );

    /* ── Status ── */
    $status = match(true) {
        $skorTotal >= 80 => 'mandiri',
        $skorTotal >= 61 => 'berpotensi_mandiri',
        $skorTotal >= 41 => 'berkembang',
        $skorTotal >= 21 => 'bergantung',
        default          => 'sangat_bergantung',
    };

    /* ── Estimasi waktu menuju mandiri ── */
    $estimasiKenaikan = 5; // asumsi naik 5 poin/bulan dengan pelatihan
    $bulanMenujuMandiri = $skorTotal >= 80 ? 0 : (int)ceil((80 - $skorTotal) / $estimasiKenaikan);

    /* ── Rekomendasi aksi ── */
    $rekomendasi = [];
    if ($skorPenghasilan < 50)    $rekomendasi[] = 'Tingkatkan penghasilan melalui pelatihan vokasional';
    if ($skorStatusKerja < 50)    $rekomendasi[] = 'Dukung anggota produktif untuk mendapat pekerjaan tetap';
    if ($skorTanggungan < 50)     $rekomendasi[] = 'Pertimbangkan program KB/pemberdayaan tanggungan';
    if (count($rekomendasi) === 0) $rekomendasi[] = 'Pertahankan perkembangan yang ada, pantau secara berkala';

    return [
        'skor_total'          => $skorTotal,
        'skor_penghasilan'    => $skorPenghasilan,
        'skor_status_kerja'   => $skorStatusKerja,
        'skor_tanggungan'     => $skorTanggungan,
        'status'              => $status,
        'estimasi_bulan_mandiri' => $bulanMenujuMandiri,
        'rekomendasi'         => $rekomendasi,
        'detail' => [
            'penghasilan'         => $penghasilan,
            'threshold'           => $thresholdPenghasilan,
            'jumlah_tanggungan'   => $tanggungan,
            'pencari_nafkah'      => $pencariNafkah,
            'anggota_produktif'   => count($anggotaProd),
        ],
    ];
}

/* ─────────────────────────────────────────────
   UPDATE skor kemandirian batch + simpan riwayat
───────────────────────────────────────────── */
function updateKemandirianBatch(PDO $pdo, bool $simpanRiwayat = false): int {
    $thres   = getKonfig($pdo, 'threshold_penghasilan_mandiri', 3500000);
    $bPeng   = getKonfig($pdo, 'bobot_penghasilan', 40);
    $bKerja  = getKonfig($pdo, 'bobot_status_kerja', 35);
    $bTangg  = getKonfig($pdo, 'bobot_tanggungan', 25);

    $wargaList = $pdo->query("
        SELECT id, penghasilan_bulanan, jumlah_tanggungan, status_pekerjaan,
               skor_kemandirian as skor_lama
        FROM rumah_warga
    ")->fetchAll(PDO::FETCH_ASSOC);

    $stmtAnggota = $pdo->prepare("
        SELECT nama, tanggal_lahir, status_bekerja, kondisi_kesehatan, dapat_bekerja
        FROM anggota_keluarga WHERE rumah_warga_id = ?
    ");
    $stmtUpdate  = $pdo->prepare("
        UPDATE rumah_warga SET skor_kemandirian = ?, status_kemandirian = ? WHERE id = ?
    ");
    $stmtRiwayat = $pdo->prepare("
        INSERT INTO riwayat_kemandirian
          (rumah_warga_id, tanggal, skor, status, penghasilan_saat_ini)
        VALUES (?, CURDATE(), ?, ?, ?)
    ");

    $updated = 0;
    foreach ($wargaList as $w) {
        $stmtAnggota->execute([(int)$w['id']]);
        $anggota = $stmtAnggota->fetchAll(PDO::FETCH_ASSOC);
        $calc    = hitungSkorKemandirian($pdo, $w, $anggota, $thres, $bPeng, $bKerja, $bTangg);

        $stmtUpdate->execute([$calc['skor_total'], $calc['status'], (int)$w['id']]);

        if ($simpanRiwayat && $calc['skor_total'] !== (int)$w['skor_lama']) {
            $stmtRiwayat->execute([
                (int)$w['id'],
                $calc['skor_total'],
                $calc['status'],
                (float)$w['penghasilan_bulanan'],
            ]);
        }
        $updated++;
    }
    return $updated;
}

/* ─────────────────────────────────────────────
   ROUTING
───────────────────────────────────────────── */
try {
    // Hanya Admin dan Petugas Lapangan yang memiliki akses ke modul kemandirian warga
    requireAuth(['admin', 'petugas']);

    $method = $_SERVER['REQUEST_METHOD'];
    $action = $_GET['action'] ?? 'list';

    if ($method === 'GET') {

        if ($action === 'list') {
            // Recalculate dulu
            updateKemandirianBatch($pdo, true);

            $statusFilter = $_GET['status'] ?? null;
            $minSkor      = (int)($_GET['min_skor'] ?? 0);
            $limit        = (int)($_GET['limit'] ?? 50);
            $thresholdSk  = getKonfig($pdo, 'threshold_skor_mandiri', 70);

            $where = [];
            if ($statusFilter) $where[] = "rw.status_kemandirian = " . $pdo->quote($statusFilter);
            if ($minSkor > 0)  $where[] = "rw.skor_kemandirian >= $minSkor";
            $whereStr = $where ? "WHERE " . implode(" AND ", $where) : "";

            $rows = $pdo->query("
                SELECT rw.id, rw.nama_kepala_keluarga, rw.no_kk,
                       rw.penghasilan_bulanan, rw.jumlah_tanggungan,
                       rw.status_pekerjaan, rw.kategori_kemiskinan,
                       rw.skor_kemandirian, rw.status_kemandirian,
                       rw.catatan_kemandirian, rw.tanggal_exit_plan,
                       rw.rekomendasi_bantuan, rw.status_bantuan,
                       rw.kelurahan, rw.kecamatan,
                       rw.latitude, rw.longitude
                FROM rumah_warga rw
                $whereStr
                ORDER BY rw.skor_kemandirian DESC
                LIMIT $limit
            ")->fetchAll(PDO::FETCH_ASSOC);

            // Tambah detail skor per row
            $thres  = getKonfig($pdo, 'threshold_penghasilan_mandiri', 3500000);
            $bPeng  = getKonfig($pdo, 'bobot_penghasilan', 40);
            $bKerja = getKonfig($pdo, 'bobot_status_kerja', 35);
            $bTangg = getKonfig($pdo, 'bobot_tanggungan', 25);
            $stmtA  = $pdo->prepare("SELECT * FROM anggota_keluarga WHERE rumah_warga_id = ?");

            foreach ($rows as &$r) {
                $stmtA->execute([(int)$r['id']]);
                $anggota = $stmtA->fetchAll(PDO::FETCH_ASSOC);
                $r['detail_skor'] = hitungSkorKemandirian($pdo, $r, $anggota, $thres, $bPeng, $bKerja, $bTangg);
            }

            $summary = $pdo->query("
                SELECT status_kemandirian, COUNT(*) as jumlah, ROUND(AVG(skor_kemandirian)) as avg_skor
                FROM rumah_warga GROUP BY status_kemandirian
            ")->fetchAll(PDO::FETCH_ASSOC);

            $siapExit = $pdo->query("
                SELECT COUNT(*) FROM rumah_warga
                WHERE skor_kemandirian >= $thresholdSk
                  AND status_bantuan != 'sudah_terima'
            ")->fetchColumn();

            echo json_encode([
                'success'   => true,
                'data'      => $rows,
                'summary'   => $summary,
                'siap_exit' => (int)$siapExit,
            ]);

        } elseif ($action === 'detail') {
            $wargaId = (int)($_GET['id'] ?? 0);

            $warga = $pdo->prepare("SELECT * FROM rumah_warga WHERE id = ?");
            $warga->execute([$wargaId]);
            $w = $warga->fetch(PDO::FETCH_ASSOC);
            if (!$w) { echo json_encode(['success' => false, 'message' => 'Warga tidak ditemukan']); exit; }

            $stmtA = $pdo->prepare("SELECT * FROM anggota_keluarga WHERE rumah_warga_id = ?");
            $stmtA->execute([$wargaId]);
            $anggota = $stmtA->fetchAll(PDO::FETCH_ASSOC);

            $thres  = getKonfig($pdo, 'threshold_penghasilan_mandiri', 3500000);
            $bPeng  = getKonfig($pdo, 'bobot_penghasilan', 40);
            $bKerja = getKonfig($pdo, 'bobot_status_kerja', 35);
            $bTangg = getKonfig($pdo, 'bobot_tanggungan', 25);

            $skor = hitungSkorKemandirian($pdo, $w, $anggota, $thres, $bPeng, $bKerja, $bTangg);

            // Riwayat
            $riwayat = $pdo->prepare("
                SELECT * FROM riwayat_kemandirian WHERE rumah_warga_id = ?
                ORDER BY tanggal DESC LIMIT 12
            ");
            $riwayat->execute([$wargaId]);

            echo json_encode([
                'success'   => true,
                'data'      => $w,
                'skor'      => $skor,
                'anggota'   => $anggota,
                'riwayat'   => $riwayat->fetchAll(PDO::FETCH_ASSOC),
            ]);

        } elseif ($action === 'statistik') {
            updateKemandirianBatch($pdo, false);
            $thresholdSk = getKonfig($pdo, 'threshold_skor_mandiri', 70);

            echo json_encode([
                'success' => true,
                'data' => [
                    'distribusi_status' => $pdo->query("
                        SELECT status_kemandirian as status, COUNT(*) as jumlah,
                               ROUND(AVG(skor_kemandirian)) as avg_skor,
                               ROUND(AVG(penghasilan_bulanan)) as avg_penghasilan
                        FROM rumah_warga GROUP BY status_kemandirian ORDER BY avg_skor DESC
                    ")->fetchAll(PDO::FETCH_ASSOC),
                    'siap_exit_plan' => (int)$pdo->query("
                        SELECT COUNT(*) FROM rumah_warga WHERE skor_kemandirian >= $thresholdSk
                    ")->fetchColumn(),
                    'sudah_punya_exit_plan' => (int)$pdo->query("
                        SELECT COUNT(*) FROM rumah_warga WHERE tanggal_exit_plan IS NOT NULL
                    ")->fetchColumn(),
                    'avg_skor_global' => (float)$pdo->query("
                        SELECT ROUND(AVG(skor_kemandirian),1) FROM rumah_warga
                    ")->fetchColumn(),
                    'trend_bulan_ini' => $pdo->query("
                        SELECT DATE(tanggal) as tgl, ROUND(AVG(skor)) as avg_skor, COUNT(*) as jumlah
                        FROM riwayat_kemandirian
                        WHERE tanggal >= DATE_SUB(NOW(), INTERVAL 30 DAY)
                        GROUP BY DATE(tanggal) ORDER BY tgl
                    ")->fetchAll(PDO::FETCH_ASSOC),
                ],
            ]);
        }

    } elseif ($method === 'POST') {
        // Catat perkembangan/catatan manual dari petugas
        $body    = json_decode(file_get_contents('php://input'), true);
        $wargaId = (int)($body['warga_id'] ?? 0);

        if (!$wargaId) { echo json_encode(['success' => false, 'message' => 'warga_id wajib']); exit; }

        $stmt = $pdo->prepare("
            UPDATE rumah_warga
            SET catatan_kemandirian = ?, tanggal_exit_plan = ?, updated_at = NOW()
            WHERE id = ?
        ");
        $stmt->execute([
            $body['catatan'] ?? null,
            $body['tanggal_exit_plan'] ?? null,
            $wargaId,
        ]);

        // Hitung ulang dan simpan ke riwayat
        $warga = $pdo->prepare("SELECT * FROM rumah_warga WHERE id = ?");
        $warga->execute([$wargaId]);
        $w = $warga->fetch(PDO::FETCH_ASSOC);

        $stmtA = $pdo->prepare("SELECT * FROM anggota_keluarga WHERE rumah_warga_id = ?");
        $stmtA->execute([$wargaId]);
        $anggota = $stmtA->fetchAll(PDO::FETCH_ASSOC);

        $thres  = getKonfig($pdo, 'threshold_penghasilan_mandiri', 3500000);
        $bPeng  = getKonfig($pdo, 'bobot_penghasilan', 40);
        $bKerja = getKonfig($pdo, 'bobot_status_kerja', 35);
        $bTangg = getKonfig($pdo, 'bobot_tanggungan', 25);
        $calc   = hitungSkorKemandirian($pdo, $w, $anggota, $thres, $bPeng, $bKerja, $bTangg);

        $pdo->prepare("
            INSERT INTO riwayat_kemandirian
              (rumah_warga_id, tanggal, skor, status, penghasilan_saat_ini, catatan)
            VALUES (?, CURDATE(), ?, ?, ?, ?)
        ")->execute([
            $wargaId, $calc['skor_total'], $calc['status'],
            (float)$w['penghasilan_bulanan'], $body['catatan'] ?? null
        ]);

        echo json_encode([
            'success' => true,
            'message' => 'Catatan kemandirian berhasil disimpan',
            'skor'    => $calc,
        ]);

    } elseif ($method === 'PUT') {
        // Update status kemandirian manual oleh admin (override sistem)
        $body    = json_decode(file_get_contents('php://input'), true);
        $wargaId = (int)($body['warga_id'] ?? 0);

        $stmt = $pdo->prepare("
            UPDATE rumah_warga
            SET status_kemandirian  = ?,
                catatan_kemandirian = ?,
                tanggal_exit_plan   = ?,
                updated_at          = NOW()
            WHERE id = ?
        ");
        $stmt->execute([
            $body['status_kemandirian'] ?? null,
            $body['catatan'] ?? null,
            $body['tanggal_exit_plan'] ?? null,
            $wargaId,
        ]);

        echo json_encode(['success' => true, 'message' => 'Status kemandirian diperbarui']);
    }

} catch (Exception $e) {
    http_response_code(500);
    echo json_encode(['success' => false, 'message' => $e->getMessage()]);
}