<?php
class FinanceController extends Controller
{
    // ── Finance Overview – company-wide financial dashboard ─
    public function overview(): void
    {
        Auth::requirePermission('finance.overview');

        $from = $this->get('from', date('Y-m-01'));
        $to   = $this->get('to',   date('Y-m-d'));

        // Sales / Purchases / Expenses summary for the period
        $sales = Database::fetchOne(
            "SELECT COALESCE(SUM(total),0) AS total, COALESCE(SUM(paid),0) AS paid,
                    COALESCE(SUM(balance),0) AS balance, COUNT(*) AS cnt
             FROM sales WHERE sale_date BETWEEN ? AND ? AND status='completed'",
            [$from.' 00:00:00', $to.' 23:59:59']
        );
        $purchases = Database::fetchOne(
            "SELECT COALESCE(SUM(total),0) AS total, COALESCE(SUM(paid),0) AS paid,
                    COALESCE(SUM(balance),0) AS balance, COUNT(*) AS cnt
             FROM purchases WHERE purchase_date BETWEEN ? AND ? AND status='received'",
            [$from, $to]
        );
        $expenses = Database::fetchOne(
            "SELECT COALESCE(SUM(amount),0) AS total, COUNT(*) AS cnt
             FROM expenses WHERE expense_date BETWEEN ? AND ?",
            [$from, $to]
        );

        // Outstanding receivables / payables (all-time, not period-bound)
        $receivables = (float) Database::fetchColumn(
            "SELECT COALESCE(SUM(current_balance),0) FROM customers WHERE current_balance > 0"
        );
        $payables = (float) Database::fetchColumn(
            "SELECT COALESCE(SUM(current_balance),0) FROM suppliers WHERE current_balance > 0"
        );

        // Pending cheques (sale = receivable, purchase = payable)
        $chequesIn = (float) Database::fetchColumn(
            "SELECT COALESCE(SUM(amount),0) FROM cheque_tracking WHERE status='pending' AND transaction_type='sale'"
        );
        $chequesOut = (float) Database::fetchColumn(
            "SELECT COALESCE(SUM(amount),0) FROM cheque_tracking WHERE status='pending' AND transaction_type='purchase'"
        );

        // Cash & Bank balances
        $accounts = [];
        try {
            $accounts = Database::fetchAll(
                "SELECT * FROM finance_accounts WHERE status='active' ORDER BY account_type, account_name"
            );
        } catch (\Exception $e) {}
        $totalCashBank = array_sum(array_column($accounts, 'current_balance'));

        // Daily cashflow chart data (last 14 days within range, capped)
        $cashflow = [];
        try {
            $cashflow = Database::fetchAll(
                "SELECT DATE(sale_date) AS d, COALESCE(SUM(paid),0) AS income
                 FROM sales WHERE sale_date BETWEEN ? AND ? AND status='completed'
                 GROUP BY DATE(sale_date) ORDER BY d",
                [$from.' 00:00:00', $to.' 23:59:59']
            );
        } catch (\Exception $e) {}

        $expenseByCat = [];
        try {
            $expenseByCat = Database::fetchAll(
                "SELECT ec.category_name, COALESCE(SUM(e.amount),0) AS total
                 FROM expenses e JOIN expense_categories ec ON ec.id = e.expense_category_id
                 WHERE e.expense_date BETWEEN ? AND ?
                 GROUP BY ec.id ORDER BY total DESC LIMIT 8",
                [$from, $to]
            );
        } catch (\Exception $e) {}

        $netProfit = (float)$sales['total'] - (float)$purchases['total'] - (float)$expenses['total'];

        $pageTitle  = 'Finance Overview';
        $breadcrumb = [['label' => 'Finance Overview']];
        ob_start();
        require APP_PATH . '/views/finance/overview.php';
        $content = ob_get_clean();
        require APP_PATH . '/views/layouts/main.php';
    }

    // ── Accounts (Cash / Bank) – list ────────────────────────
    public function accounts(): void
    {
        Auth::requirePermission('accounts.view');

        $accounts = Database::fetchAll(
            "SELECT * FROM finance_accounts ORDER BY status DESC, account_type, account_name"
        );
        $totalCash = array_sum(array_map(
            fn($a) => $a['account_type']==='cash' ? $a['current_balance'] : 0, $accounts
        ));
        $totalBank = array_sum(array_map(
            fn($a) => $a['account_type']==='bank' ? $a['current_balance'] : 0, $accounts
        ));

        $pageTitle  = 'Cash & Bank Accounts';
        $breadcrumb = [
            ['label' => 'Finance Overview', 'url' => APP_URL.'/finance/overview'],
            ['label' => 'Accounts'],
        ];
        ob_start();
        require APP_PATH . '/views/finance/accounts.php';
        $content = ob_get_clean();
        require APP_PATH . '/views/layouts/main.php';
    }

    // ── Delete transaction (developer only) ──────────────
    public function deleteTxn(string $id): void
    {
        if (Auth::role() !== 'developer') {
            redirectWith(APP_URL.'/finance/accounts','error','Developer access only.');
            return;
        }
        Auth::requireCsrf();

        $txn = Database::fetchOne(
            'SELECT * FROM finance_transactions WHERE id=?', [(int)$id]
        );
        if (!$txn) {
            redirectWith(APP_URL.'/finance/accounts','error','Transaction not found.');
            return;
        }

        $acctId = (int)$txn['account_id'];
        Database::execute('DELETE FROM finance_transactions WHERE id=?', [(int)$id]);

        Auth::logAudit(Auth::id(), 'txn_delete', 'finance_transactions',
            "Deleted txn #{$id}: {$txn['txn_type']} {$txn['amount']} on account {$acctId}"
        );

        redirectWith(
            APP_URL.'/finance/accounts/'.$acctId,
            'success',
            'Transaction deleted. Please verify account balance is correct.'
        );
    }

    // ── Edit account (admin only) ─────────────────────────────
    public function editAccount(string $id): void
    {
        if (!in_array(Auth::role(), ['super_admin','admin','developer'], true)) {
            redirectWith(APP_URL.'/finance/accounts','error','Only administrators can edit accounts.');
            return;
        }
        $account = Database::fetchOne('SELECT * FROM finance_accounts WHERE id=?', [(int)$id]);
        if (!$account) {
            redirectWith(APP_URL.'/finance/accounts','error','Account not found.');
            return;
        }
        $pageTitle  = 'Edit Account — ' . $account['account_name'];
        $breadcrumb = [
            ['label'=>'Accounts','url'=>APP_URL.'/finance/accounts'],
            ['label'=>'Edit: '.$account['account_name']],
        ];
        ob_start();
        require APP_PATH . '/views/finance/account_edit.php';
        $content = ob_get_clean();
        require APP_PATH . '/views/layouts/main.php';
    }

    // ── Update account (admin only) ───────────────────────────
    public function updateAccount(string $id): void
    {
        if (!in_array(Auth::role(), ['super_admin','admin','developer'], true)) {
            redirectWith(APP_URL.'/finance/accounts','error','Only administrators can edit accounts.');
            return;
        }
        Auth::requireCsrf();

        $account = Database::fetchOne('SELECT * FROM finance_accounts WHERE id=?', [(int)$id]);
        if (!$account) {
            redirectWith(APP_URL.'/finance/accounts','error','Account not found.');
            return;
        }

        $name    = trim($this->post('account_name',''));
        $type    = $this->post('account_type', $account['account_type']);
        $status  = $this->post('status', $account['status']);
        $bankName= $type==='bank' ? trim($this->post('bank_name','')) : null;
        $accNo   = $type==='bank' ? trim($this->post('account_number','')) : null;
        $branch  = $type==='bank' ? trim($this->post('branch','')) : null;

        if (!$name) {
            redirectWith(APP_URL.'/finance/accounts/edit/'.$id,'error','Account name is required.');
            return;
        }

        Database::execute(
            'UPDATE finance_accounts
             SET account_name=?, account_type=?, bank_name=?, account_number=?,
                 branch=?, status=?
             WHERE id=?',
            [$name, $type, $bankName, $accNo, $branch, $status, (int)$id]
        );

        Auth::logAudit(Auth::id(),'account_update','finance_accounts',"Updated account: {$name}");
        redirectWith(APP_URL.'/finance/accounts','success',"Account \"{$name}\" updated.");
    }

    // ── Create account ────────────────────────────────────────
    public function storeAccount(): void
    {
        Auth::requirePermission('accounts.manage');
        Auth::requireCsrf();

        $name = trim($this->post('account_name',''));
        $type = $this->post('account_type','cash');
        $opening = (float) $this->post('opening_balance', 0);

        if (!$name) {
            redirectWith(APP_URL.'/finance/accounts','error','Account name is required.');
            return;
        }

        Database::insert(
            'INSERT INTO finance_accounts
             (account_name, account_type, bank_name, account_number, branch, opening_balance, current_balance, status)
             VALUES (?,?,?,?,?,?,?,?)',
            [$name, $type,
             $type==='bank' ? trim($this->post('bank_name','')) : null,
             $type==='bank' ? trim($this->post('account_number','')) : null,
             $type==='bank' ? trim($this->post('branch','')) : null,
             $opening, $opening, 'active']
        );

        redirectWith(APP_URL.'/finance/accounts','success',"Account \"{$name}\" created.");
    }

    // ── Account ledger / detail ──────────────────────────────
    public function accountLedger(string $id): void
    {
        Auth::requirePermission('accounts.view');

        $account = Database::fetchOne('SELECT * FROM finance_accounts WHERE id=?', [(int)$id]);
        if (!$account) {
            redirectWith(APP_URL.'/finance/accounts','error','Account not found.');
            return;
        }

        // Filters
        $filterFrom = trim($this->get('from',''));
        $filterTo   = trim($this->get('to',''));
        $filterType = trim($this->get('type',''));

        $where  = ['t.account_id = ?'];
        $params = [(int)$id];

        if ($filterFrom) {
            $where[]  = 't.txn_date >= ?';
            $params[] = $filterFrom;
        }
        if ($filterTo) {
            $where[]  = 't.txn_date <= ?';
            $params[] = $filterTo;
        }
        if ($filterType && in_array($filterType,['deposit','withdrawal','transfer_in','transfer_out'],true)) {
            $where[]  = 't.txn_type = ?';
            $params[] = $filterType;
        }

        $txns = Database::fetchAll(
            "SELECT t.*, ra.account_name AS related_account_name, u.name AS done_by
             FROM finance_transactions t
             LEFT JOIN finance_accounts ra ON ra.id = t.related_account_id
             LEFT JOIN users u ON u.id = t.created_by
             WHERE " . implode(' AND ', $where) . "
             ORDER BY t.txn_date DESC, t.id DESC LIMIT 500",
            $params
        );

        $otherAccounts = Database::fetchAll(
            "SELECT id, account_name, account_type, current_balance
             FROM finance_accounts WHERE id != ? AND status='active'
             ORDER BY account_type, account_name",
            [(int)$id]
        );

        $pageTitle  = $account['account_name'];
        $breadcrumb = [
            ['label' => 'Accounts', 'url' => APP_URL.'/finance/accounts'],
            ['label' => $account['account_name']],
        ];
        ob_start();
        require APP_PATH . '/views/finance/account_ledger.php';
        $content = ob_get_clean();
        require APP_PATH . '/views/layouts/main.php';
    }

    // ── Deposit / Withdraw ────────────────────────────────────
    public function transaction(string $id): void
    {
        Auth::requirePermission('accounts.manage');
        Auth::requireCsrf();

        $accountId = (int)$id;
        $type      = $this->post('txn_type'); // deposit|withdrawal
        $amount    = (float) $this->post('amount', 0);
        $note      = trim($this->post('note',''));
        $reference = trim($this->post('reference',''));
        $date      = $this->post('txn_date', date('Y-m-d'));

        if ($amount <= 0 || !in_array($type, ['deposit','withdrawal'], true)) {
            redirectWith(APP_URL.'/finance/accounts/'.$accountId, 'error', 'Invalid transaction.');
            return;
        }

        $account = Database::fetchOne('SELECT * FROM finance_accounts WHERE id=?', [$accountId]);
        if (!$account) {
            redirectWith(APP_URL.'/finance/accounts','error','Account not found.');
            return;
        }

        if ($type === 'withdrawal' && $amount > (float)$account['current_balance']) {
            redirectWith(APP_URL.'/finance/accounts/'.$accountId, 'error',
                'Insufficient balance for this withdrawal.');
            return;
        }

        Database::beginTransaction();
        try {
            $newBal = $type === 'deposit'
                ? round((float)$account['current_balance'] + $amount, 2)
                : round((float)$account['current_balance'] - $amount, 2);

            Database::execute('UPDATE finance_accounts SET current_balance=? WHERE id=?', [$newBal, $accountId]);

            Database::execute(
                'INSERT INTO finance_transactions
                 (account_id, txn_type, amount, balance_after, reference, note, txn_date, created_by)
                 VALUES (?,?,?,?,?,?,?,?)',
                [$accountId, $type, $amount, $newBal, $reference ?: null, $note ?: null, $date, Auth::id()]
            );

            Database::commit();
            $label = $type === 'deposit' ? 'Deposit' : 'Withdrawal';
            Auth::logAudit(Auth::id(), 'finance_txn', 'accounts',
                "{$label} of {$amount} on {$account['account_name']}");

            redirectWith(APP_URL.'/finance/accounts/'.$accountId, 'success',
                "{$label} of " . number_format($amount,2) . ' recorded.');
        } catch (\Exception $e) {
            Database::rollback();
            redirectWith(APP_URL.'/finance/accounts/'.$accountId, 'error',
                'Transaction failed: ' . $e->getMessage());
        }
    }

    // ── Transfer between accounts ─────────────────────────────
    public function transfer(string $id): void
    {
        Auth::requirePermission('accounts.manage');
        Auth::requireCsrf();

        $fromId = (int)$id;
        $toId   = (int) $this->post('to_account_id', 0);
        $amount = (float) $this->post('amount', 0);
        $note   = trim($this->post('note',''));
        $date   = $this->post('txn_date', date('Y-m-d'));

        if (!$toId || $toId === $fromId || $amount <= 0) {
            redirectWith(APP_URL.'/finance/accounts/'.$fromId, 'error', 'Invalid transfer.');
            return;
        }

        $from = Database::fetchOne('SELECT * FROM finance_accounts WHERE id=?', [$fromId]);
        $to   = Database::fetchOne('SELECT * FROM finance_accounts WHERE id=?', [$toId]);
        if (!$from || !$to) {
            redirectWith(APP_URL.'/finance/accounts','error','Account not found.');
            return;
        }
        if ($amount > (float)$from['current_balance']) {
            redirectWith(APP_URL.'/finance/accounts/'.$fromId, 'error',
                'Insufficient balance for this transfer.');
            return;
        }

        Database::beginTransaction();
        try {
            $fromBal = round((float)$from['current_balance'] - $amount, 2);
            $toBal   = round((float)$to['current_balance']   + $amount, 2);

            Database::execute('UPDATE finance_accounts SET current_balance=? WHERE id=?', [$fromBal, $fromId]);
            Database::execute('UPDATE finance_accounts SET current_balance=? WHERE id=?', [$toBal,   $toId]);

            Database::execute(
                'INSERT INTO finance_transactions
                 (account_id, txn_type, amount, balance_after, related_account_id, note, txn_date, created_by)
                 VALUES (?,"transfer_out",?,?,?,?,?,?)',
                [$fromId, $amount, $fromBal, $toId, $note ?: null, $date, Auth::id()]
            );
            Database::execute(
                'INSERT INTO finance_transactions
                 (account_id, txn_type, amount, balance_after, related_account_id, note, txn_date, created_by)
                 VALUES (?,"transfer_in",?,?,?,?,?,?)',
                [$toId, $amount, $toBal, $fromId, $note ?: null, $date, Auth::id()]
            );

            Database::commit();
            Auth::logAudit(Auth::id(), 'finance_transfer', 'accounts',
                "Transferred {$amount} from {$from['account_name']} to {$to['account_name']}");

            redirectWith(APP_URL.'/finance/accounts/'.$fromId, 'success',
                'Transfer of ' . number_format($amount,2) . " to {$to['account_name']} completed.");
        } catch (\Exception $e) {
            Database::rollback();
            redirectWith(APP_URL.'/finance/accounts/'.$fromId, 'error',
                'Transfer failed: ' . $e->getMessage());
        }
    }

    // ── Credit Book – all credit customers ──────────────────
    public function creditBook(): void
    {
        Auth::requirePermission('credit_book.view');

        $search = trim($this->get('search', ''));
        $sortBy = $this->get('sort', 'balance');

        // Build search condition
        $searchWhere  = '';
        $searchParams = [];
        if ($search) {
            $searchWhere  = ' AND (c.customer_name LIKE ? OR c.phone LIKE ? OR c.email LIKE ?)';
            $searchParams = ["%$search%", "%$search%", "%$search%"];
        }

        $orderBy = match($sortBy) {
            'name'     => 'c.customer_name ASC',
            'last_txn' => 'last_txn DESC',
            default    => 'outstanding_balance DESC',
        };

        // Only show customers who have actual unpaid credit sales
        // (payment_method='credit' + sales.balance > 0)
        $customers = Database::fetchAll(
            "SELECT c.*,
                    SUM(s.balance)                       AS outstanding_balance,
                    SUM(s.total)                         AS total_credit_given,
                    COUNT(s.id)                          AS open_invoices,
                    MAX(s.sale_date)                     AS last_txn
             FROM customers c
             INNER JOIN sales s ON s.customer_id = c.id
                                AND s.status = 'completed'
                                AND s.balance > 0.001
             WHERE c.status = 'active'
               AND EXISTS (
                   SELECT 1 FROM sale_payments sp
                   WHERE sp.sale_id = s.id AND sp.payment_method = 'credit'
               )
               $searchWhere
             GROUP BY c.id
             HAVING outstanding_balance > 0.001
             ORDER BY $orderBy",
            $searchParams
        );

        // Summary totals
        $totalOutstanding = (float) array_sum(array_column($customers, 'outstanding_balance'));
        $totalCustomers   = count($customers);
        $totalInvoices    = (int) array_sum(array_column($customers, 'open_invoices'));

        // Over credit limit
        $overLimit = array_filter($customers,
            fn($c) => (float)$c['credit_limit'] > 0
                   && (float)$c['outstanding_balance'] >= (float)$c['credit_limit']
        );

        $pageTitle  = 'Credit Book';
        $breadcrumb = [['label' => 'Finance'], ['label' => 'Credit Book']];
        ob_start();
        require APP_PATH . '/views/finance/credit_book.php';
        $content = ob_get_clean();
        require APP_PATH . '/views/layouts/main.php';
    }

    // ── Credit Book – single customer ledger ─────────────────
    public function creditBookCustomer(string $id): void
    {
        Auth::requirePermission('credit_book.view');

        $customer = Database::fetchOne(
            'SELECT * FROM customers WHERE id = ? AND status = \'active\'',
            [(int)$id]
        );
        if (!$customer) { redirectWith(APP_URL . '/finance/credit-book', 'error', 'Customer not found.'); return; }

        // All credit transactions
        $transactions = Database::fetchAll(
            "SELECT s.id, s.invoice_no, s.sale_date, s.total, s.paid, s.balance,
                    s.payment_status, s.note,
                    u.name AS cashier
             FROM sales s
             LEFT JOIN users u ON u.id = s.created_by
             WHERE s.customer_id = ? AND s.status = 'completed'
             ORDER BY s.sale_date DESC, s.id DESC",
            [(int)$id]
        );

        // Payment history
        $payments = Database::fetchAll(
            "SELECT cp.*, u.name AS recorded_by
             FROM customer_payments cp
             LEFT JOIN users u ON u.id = cp.created_by
             WHERE cp.customer_id = ?
             ORDER BY cp.payment_date DESC, cp.id DESC",
            [(int)$id]
        );

        // Merge and sort for a running ledger
        $ledger = [];
        foreach ($transactions as $t) {
            $ledger[] = [
                'date'        => $t['sale_date'],
                'type'        => 'sale',
                'ref'         => $t['invoice_no'],
                'sale_id'     => $t['id'],
                'debit'       => (float)$t['total'],   // amount owed
                'credit'      => (float)$t['paid'],    // amount paid at time of sale
                'balance'     => (float)$t['balance'],
                'note'        => $t['note'],
                'by'          => $t['cashier'],
                'pmt_status'  => $t['payment_status'],
            ];
        }
        foreach ($payments as $p) {
            $ledger[] = [
                'date'    => $p['payment_date'],
                'type'    => 'payment',
                'ref'     => 'PMT-' . str_pad($p['id'], 4, '0', STR_PAD_LEFT),
                'sale_id' => $p['sale_id'],
                'debit'   => 0,
                'credit'  => (float)$p['amount'],
                'balance' => 0,
                'note'    => $p['note'],
                'by'      => $p['recorded_by'],
                'method'  => $p['payment_method'],
            ];
        }
        // Sort by date desc
        usort($ledger, fn($a,$b) => strcmp($b['date'], $a['date']));

        $totalDebit  = array_sum(array_column(
            array_filter($ledger, fn($l) => $l['type']==='sale'), 'debit'
        ));
        $totalPaid   = array_sum(array_column(
            array_filter($ledger, fn($l) => $l['type']==='sale'), 'credit'
        )) + array_sum(array_column(
            array_filter($ledger, fn($l) => $l['type']==='payment'), 'credit'
        ));

        $pageTitle  = 'Credit Ledger – ' . $customer['customer_name'];
        $breadcrumb = [
            ['label' => 'Finance'],
            ['label' => 'Credit Book', 'url' => APP_URL . '/finance/credit-book'],
            ['label' => $customer['customer_name']],
        ];
        ob_start();
        require APP_PATH . '/views/finance/credit_book_customer.php';
        $content = ob_get_clean();
        require APP_PATH . '/views/layouts/main.php';
    }

    // ── Record payment ────────────────────────────────────────
    public function recordPayment(string $id): void
    {
        Auth::requirePermission('credit_book.manage');
        Auth::requireCsrf();

        $customerId = (int)$id;
        $amount     = (float) $this->post('amount', 0);
        $method     = $this->post('payment_method', 'cash');
        $note       = trim($this->post('note', ''));
        $saleId     = (int) $this->post('sale_id', 0) ?: null;
        $date       = $this->post('payment_date', date('Y-m-d'));

        if ($amount <= 0) {
            redirectWith(APP_URL . '/finance/credit-book/' . $customerId, 'error', 'Amount must be greater than zero.');
            return;
        }

        $customer = Database::fetchOne('SELECT * FROM customers WHERE id = ?', [$customerId]);
        if (!$customer) {
            redirectWith(APP_URL . '/finance/credit-book', 'error', 'Customer not found.');
            return;
        }

        Database::beginTransaction();
        try {
            // Record the payment entry
            Database::execute(
                'INSERT INTO customer_payments
                 (customer_id, sale_id, amount, payment_date, payment_method, note, created_by)
                 VALUES (?, ?, ?, ?, ?, ?, ?)',
                [$customerId, $saleId ?: null, $amount, $date, $method, $note ?: null, Auth::id()]
            );

            // Reduce customer overall balance
            Database::execute(
                'UPDATE customers SET current_balance = GREATEST(0, current_balance - ?) WHERE id = ?',
                [$amount, $customerId]
            );

            if ($saleId) {
                // ── Apply to specific sale ───────────────────────
                Database::execute(
                    "UPDATE sales SET
                       paid           = paid + ?,
                       balance        = GREATEST(0, balance - ?),
                       payment_status = CASE
                         WHEN GREATEST(0, balance - ?) <= 0.01 THEN 'paid'
                         ELSE 'partial'
                       END
                     WHERE id = ?",
                    [$amount, $amount, $amount, $saleId]
                );
            } else {
                // ── Auto-distribute across outstanding credit sales (oldest first) ──
                $outstanding = Database::fetchAll(
                    "SELECT s.id, s.balance FROM sales s
                     WHERE s.customer_id = ?
                       AND s.status = 'completed'
                       AND s.balance > 0
                       AND EXISTS (
                           SELECT 1 FROM sale_payments sp
                           WHERE sp.sale_id = s.id AND sp.payment_method = 'credit'
                       )
                     ORDER BY s.sale_date ASC, s.id ASC",
                    [$customerId]
                );

                $remaining = $amount;
                foreach ($outstanding as $sale) {
                    if ($remaining <= 0) break;
                    $apply     = min($remaining, (float)$sale['balance']);
                    $remaining = round($remaining - $apply, 2);

                    Database::execute(
                        "UPDATE sales SET
                           paid           = paid + ?,
                           balance        = GREATEST(0, balance - ?),
                           payment_status = CASE
                             WHEN GREATEST(0, balance - ?) <= 0.01 THEN 'paid'
                             ELSE 'partial'
                           END
                         WHERE id = ?",
                        [$apply, $apply, $apply, (int)$sale['id']]
                    );
                }
            }

            Database::commit();
        } catch (Exception $e) {
            Database::rollback();
            redirectWith(APP_URL . '/finance/credit-book/' . $customerId,
                'error', 'Payment failed: ' . $e->getMessage());
            return;
        }

        Auth::logAudit(Auth::id(), 'credit_payment', 'finance',
            "Credit payment Rs.{$amount} from {$customer['customer_name']}");

        redirectWith(APP_URL . '/finance/credit-book/' . $customerId, 'success',
            'Payment of ' . currency($amount) . ' recorded for ' . $customer['customer_name']);
    }
}