<?php
namespace App\Controllers;

use App\Core\Acl;
use App\Core\Controller;
use App\Core\Dates;
use App\Core\Flash;
use App\Core\Request;
use App\Services\DataQualityService;
use App\Services\ExportService;
use App\Services\RevisionService;

/** Laporan & perbaikan kualitas data. */
class DataQualityController extends Controller
{
    protected string $module = 'kualitas_data';

    private function filters(): array
    {
        $f = PiutangController::readFilters(false);
        [$s, $sp] = Acl::invoiceScopeSql('i');
        $f['_scope_sql'] = $s;
        $f['_scope_params'] = $sp;
        return $f;
    }

    public function index(): void
    {
        $f = $this->filters();
        $this->view('kualitas_data/index', [
            'judul' => 'Laporan Kualitas Data',
            'subjudul' => 'Pemeriksaan berkelanjutan atas konsistensi data piutang',
            'checks' => DataQualityService::summary($f),
            'flags' => DataQualityService::importFlags(),
            'duplicates' => DataQualityService::duplicates(),
            'rekonsiliasi' => DataQualityService::excelReconciliation(80),
            'rfGaps' => RevisionService::numberingGaps(),
            'filters' => PiutangController::readFilters(false),
        ]);
    }

    public function detail(): void
    {
        $key = (string)Request::get('pemeriksaan', '');
        [$page, $per] = $this->pageParams();
        $res = DataQualityService::detail($key, $this->filters(), $page, $per);
        if (empty($res['pemeriksaan'])) {
            Flash::error('Pemeriksaan kualitas data tidak dikenali.');
            $this->redirect('/kualitas-data');
        }
        $this->view('kualitas_data/detail', [
            'judul' => 'Kualitas Data — ' . $res['pemeriksaan']['label'],
            'subjudul' => 'Tingkat ' . ucfirst($res['pemeriksaan']['tingkat']) . ' · ' . $res['pemeriksaan']['saran'],
            'p' => $res, 'pemeriksaan' => $res['pemeriksaan'], 'key' => $key,
        ]);
    }

    public function export(): void
    {
        $key = (string)Request::get('pemeriksaan', '');
        if ($key !== '') {
            $res = DataQualityService::detail($key, $this->filters(), 1, 50000);
            ExportService::send((string)Request::get('format', 'xlsx'), [
                'judul' => 'LAPORAN KUALITAS DATA — ' . mb_strtoupper($res['pemeriksaan']['label'] ?? ''),
                'subjudul' => 'Saran tindak lanjut: ' . ($res['pemeriksaan']['saran'] ?? '-'),
                'tanggal_lapor' => Dates::fmt(Dates::today()),
                'nama_berkas' => 'kualitas_data_' . $key, 'sheet' => 'Detail', 'orientasi' => 'landscape',
            ], [
                ['label' => 'No. Invoice',   'key' => 'invoice_no',   'type' => 'text'],
                ['label' => 'Faktur Pajak',  'key' => 'tax_invoice_no', 'type' => 'text'],
                ['label' => 'Tgl Invoice',   'key' => 'invoice_date', 'type' => 'date'],
                ['label' => 'Tgl Kirim',     'key' => 'sent_date',    'type' => 'date'],
                ['label' => 'Jatuh Tempo',   'key' => 'due_date',     'type' => 'date'],
                ['label' => 'Customer',      'key' => 'customer_name','type' => 'text'],
                ['label' => 'Area',          'key' => 'area_name',    'type' => 'text'],
                ['label' => 'Nominal',       'key' => 'gross_amount', 'type' => 'money'],
                ['label' => 'PPh 23',        'key' => 'pph23_amount', 'type' => 'money'],
                ['label' => 'Tarif PPh (%)', 'key' => 'pph23_rate',   'type' => 'dec'],
                ['label' => 'Total Tagihan', 'key' => 'net_amount',   'type' => 'money'],
                ['label' => 'Dibayar',       'key' => 'paid_amount',  'type' => 'money'],
                ['label' => 'Saldo',         'key' => 'outstanding_amount', 'type' => 'money'],
                ['label' => 'Status',        'key' => 'payment_status_name','type' => 'text'],
                ['label' => 'Status Dokumen','key' => 'doc_status',   'type' => 'text'],
                ['label' => 'Sheet Sumber',  'key' => 'source_sheet', 'type' => 'text'],
                ['label' => 'Tanda Masalah', 'key' => 'dq_flags',     'type' => 'text'],
            ], $res['data']);
        }

        $checks = DataQualityService::summary($this->filters());
        $rows = array_map(fn($c) => [
            'tingkat' => ucfirst($c['tingkat']), 'pemeriksaan' => $c['label'],
            'jumlah' => $c['jumlah'], 'bruto' => $c['nilai_bruto'], 'saldo' => $c['nilai_saldo'], 'saran' => $c['saran'],
        ], array_values($checks));

        ExportService::send((string)Request::get('format', 'xlsx'), [
            'judul' => 'RINGKASAN KUALITAS DATA PIUTANG',
            'tanggal_lapor' => Dates::fmt(Dates::today()),
            'nama_berkas' => 'ringkasan_kualitas_data', 'sheet' => 'Kualitas Data', 'orientasi' => 'landscape',
        ], [
            ['label' => 'Tingkat',            'key' => 'tingkat',     'type' => 'text', 'width' => 12],
            ['label' => 'Pemeriksaan',        'key' => 'pemeriksaan', 'type' => 'text', 'width' => 56, 'pdf_width' => 3],
            ['label' => 'Jumlah Invoice',     'key' => 'jumlah',      'type' => 'int'],
            ['label' => 'Nilai Bruto',        'key' => 'bruto',       'type' => 'money'],
            ['label' => 'Nilai Saldo',        'key' => 'saldo',       'type' => 'money'],
            ['label' => 'Saran Tindak Lanjut','key' => 'saran',       'type' => 'text', 'width' => 60, 'pdf_width' => 3],
        ], $rows);
    }

    public function autoFix(): void
    {
        $res = DataQualityService::autoFix();
        Flash::success('Perbaikan otomatis selesai: '
            . $res['saldo_invoice_nonaktif_dinolkan'] . ' saldo invoice non-aktif dinolkan, '
            . $res['revenue_dobel_diperbaiki'] . ' revenue dobel diperbaiki, '
            . $res['revisi_dicocokkan_ulang'] . ' revisi dicocokkan ulang, '
            . $res['janji_bayar_dievaluasi'] . ' janji bayar dievaluasi.');
        $this->redirect('/kualitas-data');
    }
}
