if ($type === 'sales' || $type === 'purchases') { $table = ($type === 'sales') ? 'invoices' : 'purchases'; $cust_table = ($type === 'sales') ? 'customers' : 'suppliers'; $cust_col = ($type === 'sales') ? 'customer_id' : 'supplier_id'; $where = ["1=1"]; $params = []; if (!empty($_GET['search'])) { $s = $_GET['search']; $clean_id = preg_replace('/[^0-9]/', '', $s); if ($clean_id !== '') { $where[] = "(v.id LIKE ? OR c.name LIKE ? OR v.id = ?)"; $params[] = "%$s%"; $params[] = "%$s%"; $params[] = $clean_id; } else { $where[] = "(v.id LIKE ? OR c.name LIKE ?)"; $params[] = "%$s%"; $params[] = "%$s%"; } } if (!empty($_GET['customer_id'])) { $where[] = "v.$cust_col = ?"; $params[] = $_GET['customer_id']; } if (!empty($_GET['start_date'])) { $where[] = "v.invoice_date >= ?"; $params[] = $_GET['start_date']; } if (!empty($_GET['end_date'])) { $where[] = "v.invoice_date <= ?"; $params[] = $_GET['end_date']; } $whereSql = implode(" AND ", $where); -- $stmt->execute($params); $headers = ['Invoice ID', 'Customer/Supplier', 'Date', 'Payment', 'Status', 'Total', 'Paid', 'Balance']; while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) $rows[] = $row; } elseif ($type === 'customers' || $type === 'suppliers') { $table = ($type === 'suppliers') ? 'suppliers' : 'customers'; $where = ["1=1"]; $params = []; if (!empty($_GET['search'])) { $where[] = "(name LIKE ? OR email LIKE ? OR phone LIKE ? OR tax_id LIKE ?)"; $params[] = "%{$_GET['search']}%"; $params[] = "%{$_GET['search']}%"; $params[] = "%{$_GET['search']}%"; $params[] = "%{$_GET['search']}%"; } if (!empty($_GET['start_date'])) { $where[] = "DATE(created_at) >= ?"; $params[] = $_GET['start_date']; } if (!empty($_GET['end_date'])) { $where[] = "DATE(created_at) <= ?"; $params[] = $_GET['end_date']; } $whereSql = implode(" AND ", $where); $stmt = db()->prepare("SELECT id, name, email, phone, tax_id, balance, created_at FROM $table WHERE $whereSql ORDER BY id DESC"); $stmt->execute($params); $headers = ['ID', 'Name', 'Email', 'Phone', 'Tax ID', 'Balance', 'Created At']; while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) $rows[] = $row; } elseif ($type === 'items') { $where = ["1=1"]; $params = []; if (!empty($_GET['search'])) { $where[] = "(i.name_en LIKE ? OR i.name_ar LIKE ? OR i.sku LIKE ?)"; $params[] = "%{$_GET['search']}%"; $params[] = "%{$_GET['search']}%"; $params[] = "%{$_GET['search']}%"; } $whereSql = implode(" AND ", $where); $stmt = db()->prepare("SELECT i.sku, i.name_en, i.name_ar, c.name_en as category, i.purchase_price, i.sale_price, i.stock_quantity, i.vat_rate FROM stock_items i LEFT JOIN stock_categories c ON i.category_id = c.id WHERE $whereSql ORDER BY i.id DESC"); $stmt->execute($params); $headers = ['SKU', 'Name (EN)', 'Name (AR)', 'Category', 'Purchase Price', 'Sale Price', 'Quantity', 'VAT %']; while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) $rows[] = $row; } elseif ($type === 'expenses') { $where = ["1=1"]; $params = []; $stmt = db()->prepare("SELECT e.id, c.name_en as category, e.amount, e.expense_date, e.reference_no, e.description FROM expenses e JOIN expense_categories c ON e.category_id = c.id ORDER BY e.expense_date DESC"); $stmt->execute(); $headers = ['ID', 'Category', 'Amount', 'Date', 'Reference', 'Description']; while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) $rows[] = $row; } elseif ($type === 'quotations') { $stmt = db()->prepare("SELECT q.id, c.name as customer_name, q.quotation_date, q.total_with_vat, q.status FROM quotations q JOIN customers c ON q.customer_id = c.id ORDER BY q.id DESC"); $stmt->execute(); $headers = ['Quotation #', 'Customer', 'Date', 'Total', 'Status']; while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) $rows[] = $row; } elseif ($type === 'lpos') { $stmt = db()->prepare("SELECT q.id, s.name as supplier_name, q.lpo_date, q.total_with_vat, q.status FROM lpos q JOIN suppliers s ON q.supplier_id = s.id ORDER BY q.id DESC"); $stmt->execute(); $headers = ['LPO #', 'Supplier', 'Date', 'Total', 'Status']; -- $page_num = isset($_GET["p"]) ? (int)$_GET["p"] : 1; if ($page_num < 1) $page_num = 1; $offset = ($page_num - 1) * $limit; switch ($page) { case 'suppliers': $where = ["1=1"]; $params = []; if (!empty($_GET['search'])) { $where[] = "(name LIKE ? OR email LIKE ? OR phone LIKE ? OR tax_id LIKE ?)"; $params[] = "%{$_GET['search']}%"; $params[] = "%{$_GET['search']}%"; $params[] = "%{$_GET['search']}%"; $params[] = "%{$_GET['search']}%"; } if (!empty($_GET['start_date'])) { $where[] = "DATE(created_at) >= ?"; $params[] = $_GET['start_date']; } if (!empty($_GET['end_date'])) { $where[] = "DATE(created_at) <= ?"; $params[] = $_GET['end_date']; } $whereSql = implode(" AND ", $where); $countStmt = db()->prepare("SELECT COUNT(*) FROM suppliers WHERE $whereSql"); $countStmt->execute($params); -- $stmt = db()->prepare("SELECT * FROM suppliers WHERE $whereSql ORDER BY id DESC LIMIT $limit OFFSET $offset"); $stmt->execute($params); $data['customers'] = $stmt->fetchAll(); // Keep 'customers' key for template compatibility if needed, or update template break; case 'customers': $where = ["1=1"]; $params = []; if (!empty($_GET['search'])) { $where[] = "(name LIKE ? OR email LIKE ? OR phone LIKE ? OR tax_id LIKE ?)"; $params[] = "%{$_GET['search']}%"; $params[] = "%{$_GET['search']}%"; $params[] = "%{$_GET['search']}%"; $params[] = "%{$_GET['search']}%"; } if (!empty($_GET['start_date'])) { $where[] = "DATE(created_at) >= ?"; $params[] = $_GET['start_date']; } if (!empty($_GET['end_date'])) { $where[] = "DATE(created_at) <= ?"; $params[] = $_GET['end_date']; } $whereSql = implode(" AND ", $where); $countStmt = db()->prepare("SELECT COUNT(*) FROM customers WHERE $whereSql"); $countStmt->execute($params); -- case 'units': // Already fetched globally break; case 'items': file_put_contents('debug.log', date('Y-m-d H:i:s') . " - Items case hit\n", FILE_APPEND); $where = ["1=1"]; $params = []; if (!empty($_GET['search'])) { $where[] = "(i.name_en LIKE ? OR i.name_ar LIKE ? OR i.sku LIKE ?)"; $params[] = "%{$_GET['search']}%"; $params[] = "%{$_GET['search']}%"; $params[] = "%{$_GET['search']}%"; } $whereSql = implode(" AND ", $where); $countStmt = db()->prepare("SELECT COUNT(*) FROM stock_items i LEFT JOIN stock_categories c ON i.category_id = c.id LEFT JOIN stock_units u ON i.unit_id = u.id LEFT JOIN suppliers s ON i.supplier_id = s.id WHERE $whereSql"); $countStmt->execute($params); $total_records = (int)$countStmt->fetchColumn(); $data['total_pages'] = ceil($total_records / $limit); $data['current_page'] = $page_num; $stmt = db()->prepare("SELECT i.*, c.name_en as cat_en, c.name_ar as cat_ar, u.short_name_en as unit_en, u.short_name_ar as unit_ar, s.name as supplier_name FROM stock_items i -- ORDER BY i.id DESC LIMIT $limit OFFSET $offset"); $stmt->execute($params); $data['items'] = $stmt->fetchAll(); break; case 'quotations': $where = ["1=1"]; $params = []; if (!empty($_GET['search'])) { $s = $_GET['search']; $clean_id = preg_replace('/[^0-9]/', '', $s); if ($clean_id !== '') { $where[] = "(q.id LIKE ? OR c.name LIKE ? OR q.id = ?)"; $params[] = "%$s%"; $params[] = "%$s%"; $params[] = $clean_id; } else { $where[] = "(q.id LIKE ? OR c.name LIKE ?)"; $params[] = "%$s%"; $params[] = "%$s%"; } } if (!empty($_GET['customer_id'])) { $where[] = "q.customer_id = ?"; $params[] = $_GET['customer_id']; } if (!empty($_GET['start_date'])) { -- LIMIT $limit OFFSET $offset"); $stmt->execute($params); $data['quotations'] = $stmt->fetchAll(); break; case 'lpos': $where = ["1=1"]; $params = []; if (!empty($_GET['search'])) { $s = $_GET['search']; $clean_id = preg_replace('/[^0-9]/', '', $s); if ($clean_id !== '') { $where[] = "(q.id LIKE ? OR s.name LIKE ? OR q.id = ?)"; $params[] = "%$s%"; $params[] = "%$s%"; $params[] = $clean_id; } else { $where[] = "(q.id LIKE ? OR s.name LIKE ?)"; $params[] = "%$s%"; $params[] = "%$s%"; } } if (!empty($_GET['supplier_id'])) { $where[] = "q.supplier_id = ?"; $params[] = $_GET['supplier_id']; } if (!empty($_GET['start_date'])) { -- $type = ($page === 'sales') ? 'sale' : 'purchase'; $table = ($type === 'purchase') ? 'purchases' : 'invoices'; $cust_supplier_col = ($type === 'purchase') ? 'supplier_id' : 'customer_id'; $cust_supplier_table = ($type === 'purchase') ? 'suppliers' : 'customers'; $where = ["1=1"]; $params = []; if (!empty($_GET['search'])) { $s = $_GET['search']; $clean_id = preg_replace('/[^0-9]/', '', $s); if ($clean_id !== '') { $where[] = "(v.id LIKE ? OR c.name LIKE ? OR v.id = ?)"; $params[] = "%$s%"; $params[] = "%$s%"; $params[] = $clean_id; } else { $where[] = "(v.id LIKE ? OR c.name LIKE ?)"; $params[] = "%$s%"; $params[] = "%$s%"; } } if (!empty($_GET['customer_id'])) { $where[] = "v.$cust_supplier_col = ?"; $params[] = $_GET['customer_id']; -- $data['purchase_invoices'] = db()->query("SELECT id, invoice_date, total_with_vat FROM purchases ORDER BY id DESC")->fetchAll(); } break; case 'sales_returns': $where = ["1=1"]; $params = []; if (!empty($_GET['search'])) { $s = $_GET['search']; $clean_id = preg_replace('/[^0-9]/', '', $s); if ($clean_id !== '') { $where[] = "(sr.id LIKE ? OR c.name LIKE ? OR sr.invoice_id LIKE ? OR sr.id = ? OR sr.invoice_id = ?)"; $params[] = "%$s%"; $params[] = "%$s%"; $params[] = "%$s%"; $params[] = $clean_id; $params[] = $clean_id; } else { $where[] = "(sr.id LIKE ? OR c.name LIKE ? OR sr.invoice_id LIKE ?)"; $params[] = "%$s%"; $params[] = "%$s%"; $params[] = "%$s%"; } } $whereSql = implode(" AND ", $where); $stmt = db()->prepare("SELECT sr.*, c.name as customer_name, i.total_with_vat as invoice_total -- $data['returns'] = $stmt->fetchAll(); $data['sales_invoices'] = db()->query("SELECT id, invoice_date, total_with_vat FROM invoices ORDER BY id DESC")->fetchAll(); break; case 'purchase_returns': $where = ["1=1"]; $params = []; if (!empty($_GET['search'])) { $s = $_GET['search']; $clean_id = preg_replace('/[^0-9]/', '', $s); if ($clean_id !== '') { $where[] = "(pr.id LIKE ? OR c.name LIKE ? OR pr.purchase_id LIKE ? OR pr.id = ? OR pr.purchase_id = ?)"; $params[] = "%$s%"; $params[] = "%$s%"; $params[] = "%$s%"; $params[] = $clean_id; $params[] = $clean_id; } else { $where[] = "(pr.id LIKE ? OR c.name LIKE ? OR pr.purchase_id LIKE ?)"; $params[] = "%$s%"; $params[] = "%$s%"; $params[] = "%$s%"; } } $whereSql = implode(" AND ", $where); $stmt = db()->prepare("SELECT pr.*, c.name as supplier_name, i.total_with_vat as invoice_total -- break; case 'expense_categories': $data['expense_categories'] = db()->query("SELECT * FROM expense_categories ORDER BY name_en ASC")->fetchAll(); break; case 'expenses': $where = ["1=1"]; $params = []; if (!empty($_GET['category_id'])) { $where[] = "e.category_id = ?"; $params[] = $_GET['category_id']; } if (!empty($_GET['start_date'])) { $where[] = "e.expense_date >= ?"; $params[] = $_GET['start_date']; } if (!empty($_GET['end_date'])) { $where[] = "e.expense_date <= ?"; $params[] = $_GET['end_date']; } $whereSql = implode(" AND ", $where); $stmt = db()->prepare("SELECT e.*, c.name_en as cat_en, c.name_ar as cat_ar FROM expenses e LEFT JOIN expense_categories c ON e.category_id = c.id WHERE $whereSql ORDER BY e.expense_date DESC, e.id DESC"); $stmt->execute($params); -- $data['year'] = $year; $data['payroll'] = db()->query("SELECT p.*, e.name as emp_name FROM hr_payroll p JOIN hr_employees e ON p.employee_id = e.id WHERE p.payroll_month = $month AND p.payroll_year = $year ORDER BY p.id DESC")->fetchAll(); $data['employees'] = db()->query("SELECT id, name, salary FROM hr_employees WHERE status = 'active' ORDER BY name ASC")->fetchAll(); break; case 'loyalty_history': $where = ["1=1"]; $params = []; if (!empty($_GET['customer_id'])) { $where[] = "lt.customer_id = ?"; $params[] = (int)$_GET['customer_id']; } if (!empty($_GET['type'])) { $where[] = "lt.transaction_type = ?"; $params[] = $_GET['type']; } $whereSql = implode(" AND ", $where); $stmt = db()->prepare("SELECT lt.*, c.name as customer_name, c.loyalty_tier, c.loyalty_points FROM loyalty_transactions lt JOIN customers c ON lt.customer_id = c.id WHERE $whereSql ORDER BY lt.created_at DESC"); $stmt->execute($params); $data['loyalty_transactions'] = $stmt->fetchAll(); break; case 'devices': $data['devices'] = db()->query("SELECT * FROM hr_biometric_devices ORDER BY id DESC")->fetchAll(); -- break; case 'cash_registers': $data['cash_registers'] = db()->query("SELECT * FROM cash_registers ORDER BY id DESC")->fetchAll(); break; case 'register_sessions': $where = ["1=1"]; $params = []; // Filter by user if provided and user has permission if (isset($_GET['user_id']) && !empty($_GET['user_id'])) { if (can('users_view')) { $where[] = "s.user_id = ?"; $params[] = $_GET['user_id']; } } if (!can('users_view')) { $where[] = "s.user_id = ?"; $params[] = $_SESSION['user_id']; } // Filter by date range if (isset($_GET['date_from']) && !empty($_GET['date_from'])) { $where[] = "s.opened_at >= ?"; $params[] = $_GET['date_from'] . ' 00:00:00'; }