<?php
/**
 * Shared accounting helpers for posting references and core accounts.
 */

if (!function_exists('accNormalize')) {
    function accNormalize(string $value): string {
        return strtolower(trim($value));
    }
}

if (!function_exists('accClassifyPostingPrefix')) {
    function accClassifyPostingPrefix(mysqli $conn, array $lines, string $description = ''): string {
        $desc = accNormalize($description);
        if ($desc !== '' && (strpos($desc, 'insurance') !== false || strpos($desc, 'insur') !== false)) {
            return 'INS';
        }

        $assetIds = [];
        foreach ($lines as $line) {
            $aid = (int)($line['account_id'] ?? 0);
            if ($aid > 0) {
                $assetIds[] = $aid;
            }
        }
        if (!$assetIds) {
            return 'JV';
        }

        $assetIds = array_values(array_unique($assetIds));
        $ph = implode(',', array_fill(0, count($assetIds), '?'));
        $types = str_repeat('i', count($assetIds));

        $sql = "SELECT account_id, account_name FROM chart_of_accounts WHERE account_id IN ($ph)";
        $st = $conn->prepare($sql);
        $st->bind_param($types, ...$assetIds);
        $st->execute();
        $rs = $st->get_result();

        $names = [];
        while ($row = $rs->fetch_assoc()) {
            $names[] = accNormalize((string)$row['account_name']);
        }
        $st->close();

        foreach ($names as $name) {
            if (strpos($name, 'mpesa') !== false || strpos($name, 'm-pesa') !== false || strpos($name, 'till') !== false) {
                return 'BA';
            }
        }
        foreach ($names as $name) {
            if (strpos($name, 'bank') !== false) {
                return 'BA';
            }
        }
        foreach ($names as $name) {
            if (strpos($name, 'cash') !== false || strpos($name, 'petty') !== false) {
                return 'CA';
            }
        }
        return 'JV';
    }
}

if (!function_exists('accGenerateJournalNumberByPrefix')) {
    function accGenerateJournalNumberByPrefix(mysqli $conn, string $prefix): string {
        $prefix = strtoupper(trim($prefix));
        if ($prefix === '') {
            $prefix = 'JV';
        }
        $year = date('Y');
        $like = $prefix . '-' . $year . '-%';
        $sql = "SELECT MAX(CAST(SUBSTRING_INDEX(journal_number, '-', -1) AS UNSIGNED)) AS mx
                FROM journal_entries
                WHERE journal_number LIKE ?";
        $st = $conn->prepare($sql);
        $st->bind_param('s', $like);
        $st->execute();
        $row = $st->get_result()->fetch_assoc();
        $st->close();
        $next = ((int)($row['mx'] ?? 0)) + 1;
        return $prefix . '-' . $year . '-' . str_pad((string)$next, 6, '0', STR_PAD_LEFT);
    }
}

if (!function_exists('accEnsureReconciliationAccounts')) {
    function accEnsureReconciliationAccounts(mysqli $conn): void {
        $needed = [
            ['1105', 'Reconciliation Bank Clearing', 'Current Assets'],
            ['1110', 'Reconciliation Cash Clearing', 'Current Assets'],
            ['1115', 'Reconciliation MPESA Till Clearing', 'Current Assets'],
        ];

        $ins = $conn->prepare(
            "INSERT INTO chart_of_accounts
             (account_code, account_name, account_type, account_category, is_header, normal_balance, current_balance, opening_balance, is_active)
             VALUES (?, ?, 'ASSET', ?, 0, 'DEBIT', 0, 0, 1)"
        );
        foreach ($needed as $acc) {
            [$code, $name, $cat] = $acc;
            $chk = $conn->prepare("SELECT account_id FROM chart_of_accounts WHERE account_code = ? OR account_name = ? LIMIT 1");
            $chk->bind_param('ss', $code, $name);
            $chk->execute();
            $exists = $chk->get_result()->fetch_assoc();
            $chk->close();
            if ($exists) {
                continue;
            }
            $ins->bind_param('sss', $code, $name, $cat);
            $ins->execute();
        }
        $ins->close();
    }
}
?>
