<?php
require_once __DIR__ . '/../config/db.php';
require_once __DIR__ . '/../config/auth.php';
$user  = requireRole([1, 2, 3, 4, 5]);
$db    = getDB();

// lines arrives as JSON string from URLSearchParams
$rawLines = $_POST['lines'] ?? '';
if (is_string($rawLines) && strlen($rawLines) > 0) {
    $lines = json_decode($rawLines, true) ?: [];
} elseif (is_array($rawLines)) {
    $lines = $rawLines;
} else {
    $lines = [];
}
if (empty($lines)) apiError('No items provided.', 422);
$jobCardId = post('job_card_id') !== '' ? (int)post('job_card_id') : null;
$projectId = post('project_id')  !== '' ? (int)post('project_id')  : null;
$notes     = post('notes', '');
$txType    = $jobCardId ? 'issue_jobcard' : ($projectId ? 'issue_project' : 'issue_person');
$refNo     = 'ISS-' . date('YmdHis');

try {
    $db->beginTransaction();
    $lowStockAlerts = [];

    foreach ($lines as $line) {
        $itemId = (int)($line['item_id'] ?? 0);
        $qty    = (float)($line['qty'] ?? 0);
        if (!$itemId || $qty <= 0) continue;

        // Check total available across all locations
        $availStmt = $db->prepare("SELECT SUM(quantity) AS total FROM stock_inventory WHERE stock_item_id=?");
        $availStmt->execute([$itemId]);
        $available = (float)($availStmt->fetchColumn() ?? 0);

        if ($available < $qty) {
            $db->rollBack();
            $nm = $db->query("SELECT name FROM stock_items WHERE id=$itemId")->fetchColumn();
            apiError("Insufficient stock for '$nm'. Available: $available.", 422);
        }

        // Get unit cost
        $ucRow = $db->prepare("SELECT unit_cost, min_qty FROM stock_items WHERE id=?");
        $ucRow->execute([$itemId]);
        $item = $ucRow->fetch();
        $unitCost = $item ? (float)$item['unit_cost'] : null;

        // Record transaction
        $db->prepare("
            INSERT INTO stock_transactions
                (stock_item_id, transaction_type, quantity, unit_cost, user_id, job_card_id, project_id, reference_no, notes, transaction_date)
            VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, NOW())
        ")->execute([$itemId, $txType, $qty, $unitCost, $user['id'], $jobCardId, $projectId, $refNo, $notes]);

        // Deduct from inventory — take from each location until qty met
        $remaining = $qty;
        $locRows = $db->prepare("SELECT id, location_id, quantity FROM stock_inventory WHERE stock_item_id=? AND quantity>0 ORDER BY quantity DESC");
        $locRows->execute([$itemId]);
        foreach ($locRows->fetchAll() as $inv) {
            if ($remaining <= 0) break;
            $deduct = min($remaining, (float)$inv['quantity']);
            $db->prepare("UPDATE stock_inventory SET quantity = quantity - ? WHERE id=?")
               ->execute([$deduct, $inv['id']]);
            $remaining -= $deduct;
        }

        // Check low stock
        $newTotal = $available - $qty;
        if ($item && $newTotal <= (float)$item['min_qty']) {
            $nm = $db->query("SELECT name FROM stock_items WHERE id=$itemId")->fetchColumn();
            $lowStockAlerts[] = ['name' => $nm, 'qty' => $newTotal, 'min_qty' => $item['min_qty']];
        }
    }

    $db->commit();

    // ── Low stock email notifications ─────────────────────
    if (!empty($lowStockAlerts)) {
        try {
            require_once __DIR__ . '/../config/mailer.php';
            require_once __DIR__ . '/../emails/templates.php';

            $rule = $db->query("SELECT * FROM email_notification_rules WHERE event_type='low_stock' LIMIT 1")->fetch();
            if ($rule && $rule['is_enabled']) {
                $cfg     = getMailerConfig($db);
                $appUrl  = $cfg['email_app_url'] ?? '';

                // Build recipient list from notify_role_ids
                $recipients = [];

                // Admin email
                if ($rule['notify_admin']) {
                    $adminEmail = getAdminEmail($db);
                    if ($adminEmail) $recipients[] = ['email' => $adminEmail, 'name' => 'Admin'];
                }

                // Role-based users
                if (!empty($rule['notify_role_ids'])) {
                    $roleIds = array_filter(array_map('intval', explode(',', $rule['notify_role_ids'])));
                    if ($roleIds) {
                        $in  = implode(',', $roleIds);
                        $uStmt = $db->query("SELECT email, full_name FROM users WHERE role_id IN ({$in}) AND is_active=1 AND email IS NOT NULL AND email != ''");
                        foreach ($uStmt->fetchAll() as $u) {
                            // Avoid duplicate if admin user also matches a role
                            if (!in_array($u['email'], array_column($recipients, 'email'))) {
                                $recipients[] = ['email' => $u['email'], 'name' => $u['full_name']];
                            }
                        }
                    }
                }

                // Custom recipients
                if (!empty($rule['custom_recipients'])) {
                    foreach (array_filter(array_map('trim', explode(',', $rule['custom_recipients']))) as $em) {
                        if (filter_var($em, FILTER_VALIDATE_EMAIL) && !in_array($em, array_column($recipients, 'email'))) {
                            $recipients[] = ['email' => $em, 'name' => ''];
                        }
                    }
                }

                foreach ($recipients as $r) {
                    $html = tplLowStock($lowStockAlerts, $r['name'] ?: 'Team', $appUrl);
                    queueEmail($db, 'low_stock', $r['email'], $r['name'],
                        '⚠ Low Stock Alert — ' . count($lowStockAlerts) . ' item(s) need replenishment',
                        $html, 'stock', 0);
                }
            }
        } catch (Exception $emailErr) {
            error_log('[EWG Email] low_stock trigger failed: ' . $emailErr->getMessage());
        }
    }

    apiSuccess(['reference' => $refNo, 'low_stock_alerts' => $lowStockAlerts], 'Stock issued.');

} catch (PDOException $e) {
    if ($db->inTransaction()) $db->rollBack();
    apiError('Database error: ' . $e->getMessage(), 500);
} catch (Exception $e) {
    if ($db->inTransaction()) $db->rollBack();
    apiError('Error: ' . $e->getMessage(), 500);
}