<?php

namespace Modules\Accounting\Controllers;

use App\Controllers\BaseController;
use App\Models\SupplierBillModel;
use App\Models\SupplierModel;
use App\Traits\ExportsReport;

class PayablesAgingController extends BaseController
{
    use ExportsReport;

    protected SupplierBillModel $bills;
    protected SupplierModel $suppliers;

    public function initController(\CodeIgniter\HTTP\RequestInterface $request, \CodeIgniter\HTTP\ResponseInterface $response, \Psr\Log\LoggerInterface $logger)
    {
        parent::initController($request, $response, $logger);
        $this->bills     = new SupplierBillModel();
        $this->suppliers = new SupplierModel();
    }

    public function index()
    {
        $supplierId = $this->request->getGet('supplier_id') ? (int) $this->request->getGet('supplier_id') : null;
        $asOf       = $this->request->getGet('as_of') ?: date('Y-m-d');

        $bills = $this->bills
            ->scopeOutstanding(null, $supplierId)
            ->orderBy('supplier_bills.due_date', 'ASC')
            ->orderBy('supplier_bills.id', 'ASC')
            ->findAll();

        $buckets = [
            'current' => ['label' => 'Current', 'rows' => [], 'total' => 0.0],
            '1_30'    => ['label' => '1-30', 'rows' => [], 'total' => 0.0],
            '31_60'   => ['label' => '31-60', 'rows' => [], 'total' => 0.0],
            '61_90'   => ['label' => '61-90', 'rows' => [], 'total' => 0.0],
            '90_plus' => ['label' => '90+', 'rows' => [], 'total' => 0.0],
        ];

        $asOfTs = strtotime($asOf);
        foreach ($bills as $bill) {
            $due         = $bill['due_date'] ?: $bill['bill_date'];
            $daysOver    = (int) floor(($asOfTs - strtotime($due)) / 86400);
            $outstanding = round((float) $bill['total'] - (float) $bill['amount_paid'], 2);
            $bill['outstanding']  = $outstanding;
            $bill['days_overdue'] = max(0, $daysOver);

            if ($daysOver <= 0) {
                $key = 'current';
            } elseif ($daysOver <= 30) {
                $key = '1_30';
            } elseif ($daysOver <= 60) {
                $key = '31_60';
            } elseif ($daysOver <= 90) {
                $key = '61_90';
            } else {
                $key = '90_plus';
            }

            $buckets[$key]['rows'][] = $bill;
            $buckets[$key]['total'] += $outstanding;
        }

        $grandTotal = array_sum(array_column($buckets, 'total'));

        $sections = [];
        foreach ($buckets as $bucket) {
            $sections[] = [
                'title'   => $bucket['label'] . ' (Total ' . number_format((float) $bucket['total'], 2) . ')',
                'headers' => ['Number', 'Supplier', 'Bill Date', 'Due Date', 'Days Overdue', 'Outstanding'],
                'rows'    => array_map(static fn ($bill) => [
                    $bill['number'] ?? '',
                    $bill['supplier_name'] ?? '',
                    $bill['bill_date'] ?? '',
                    $bill['due_date'] ?? '',
                    (int) ($bill['days_overdue'] ?? 0),
                    number_format((float) ($bill['outstanding'] ?? 0), 2),
                ], $bucket['rows']),
            ];
        }

        if ($export = $this->exportSections(
            'payables_aging',
            'Payables Aging',
            $sections,
            'As of ' . $asOf . ' | Grand total ' . number_format((float) $grandTotal, 2)
        )) {
            return $export;
        }

        return view('Modules\Accounting\Views\payables_aging\index', array_merge($this->baseViewData(), [
            'title'      => 'Payables Aging',
            'suppliers'  => $this->suppliers->getActive(),
            'buckets'    => $buckets,
            'grandTotal' => round($grandTotal, 2),
            'filters'    => compact('supplierId', 'asOf'),
        ]));
    }
}
