getConnection(); // --- Input --- $name = trim($_POST['name'] ?? ''); $surname = trim($_POST['surname'] ?? ''); $email = trim($_POST['email'] ?? ''); $userid = isset($_POST['userid']) ? (int) $_POST['userid'] : 0; $idserviceschedule = isset($_POST['idserviceschedule']) ? (int) $_POST['idserviceschedule'] : 0; $status = trim($_POST['status'] ?? 'booked'); $idservice = isset($_POST['idservice']) ? (int) $_POST['idservice'] : 0; $bookingstart = trim($_POST['bookingstart'] ?? ''); // Nuovi campi dal modale $bkmode = trim($_POST['bkmode'] ?? 'scala'); // scala | omaggio | nuovo $idorderRaw = $_POST['idorder'] ?? ''; $newExpiry = trim($_POST['new_expiry'] ?? ''); // --- Validazione minima --- if ($idserviceschedule <= 0 || $idservice <= 0) { header('Location: adminpanel.php?error=missingdata'); exit; } try { $pdo->beginTransaction(); // ------------------------------------------------------------------ // 1) Risolvi / crea utente // ------------------------------------------------------------------ if ($userid <= 0) { if ($email !== '') { $check = $pdo->prepare("SELECT id FROM auth_users WHERE email = :email LIMIT 1"); $check->execute([':email' => $email]); $existing = $check->fetchColumn(); if ($existing) { $userid = (int) $existing; } } if ($userid <= 0) { $randomPassword = bin2hex(random_bytes(8)); $hashed = password_hash($randomPassword, PASSWORD_BCRYPT); $insUser = $pdo->prepare( "INSERT INTO auth_users (first_name, last_name, email, password, role_id, status, created_at, avatar) VALUES (:first, :last, :email, :password, :role, :status, :created, :avatar)" ); $insUser->execute([ ':first' => $name, ':last' => $surname, ':email' => $email !== '' ? $email : null, ':password' => $hashed, ':role' => 2, ':status' => 'Active', ':created' => date('Y-m-d H:i:s'), ':avatar' => 'mediationb.png', ]); $userid = (int) $pdo->lastInsertId(); } } // ------------------------------------------------------------------ // 2) Determina idorder e is_gift in base alla modalità // ------------------------------------------------------------------ $idorder = null; // default NULL (rispetta la FK) $isGift = 'N'; if ($bkmode === 'omaggio') { // Omaggio: nessun ordine, flag gift $idorder = null; $isGift = 'Y'; } elseif ($bkmode === 'nuovo') { // Crea un nuovo ordine con 1 ticket, maxreschedule 0 if ($newExpiry === '') { throw new RuntimeException('Scadenza mancante per il nuovo ordine.'); } // Recupera i dati reali dell'utente (email, nome, cognome) $uStmt = $pdo->prepare( "SELECT first_name, last_name, email FROM auth_users WHERE id = :uid LIMIT 1" ); $uStmt->execute([':uid' => $userid]); $uRow = $uStmt->fetch() ?: []; $uEmail = $uRow['email'] ?? ($email !== '' ? $email : null); $uFirst = $uRow['first_name'] ?? $name; $uLast = $uRow['last_name'] ?? $surname; // Recupera il nome del servizio (per cod / product_name) $sStmt = $pdo->prepare( "SELECT servicename FROM service WHERE idservice = :sid LIMIT 1" ); $sStmt->execute([':sid' => $idservice]); $serviceName = (string) ($sStmt->fetchColumn() ?: ''); // first_lesson_date = data della lezione (solo parte data di bookingstart) $firstLessonDate = null; if ($bookingstart !== '') { try { $firstLessonDate = (new DateTime($bookingstart))->format('Y-m-d'); } catch (Throwable $e) { $firstLessonDate = null; } } $insOrder = $pdo->prepare( "INSERT INTO orderbook (iduser, idservice, nticket, quantity, quantityclass, expireon, maxreschedule, reprogrammed, status, order_billing_email, cod, product_name, first_name, last_name, first_lesson_date, order_date_created) VALUES (:uid, :service, 1, 1, 1, :expire, 0, 0, 'booked', :bemail, :cod, :pname, :first, :last, :firstlesson, :created)" ); $insOrder->execute([ ':uid' => $userid, ':service' => $idservice, ':expire' => $newExpiry, ':bemail' => $uEmail, ':cod' => $serviceName, ':pname' => $serviceName, ':first' => $uFirst, ':last' => $uLast, ':firstlesson' => $firstLessonDate, ':created' => date('Y-m-d'), ]); $idorder = (int) $pdo->lastInsertId(); $isGift = 'N'; } else { // 'scala': aggancia a ordine esistente $idorder = ($idorderRaw !== '' && (int) $idorderRaw > 0) ? (int) $idorderRaw : null; // Se non è stato passato un ordine valido in modalità scala, // per sicurezza NON forziamo 0 (romperebbe la FK): resta NULL. if ($idorder !== null) { // Verifica che l'ordine sia dell'utente e non scaduto $chk = $pdo->prepare( "SELECT expireon FROM orderbook WHERE idorderbook = :oid AND iduser = :uid LIMIT 1" ); $chk->execute([':oid' => $idorder, ':uid' => $userid]); $row = $chk->fetch(); if (!$row) { throw new RuntimeException('Ordine non valido per questo utente.'); } $exp = $row['expireon'] ?? null; if ($exp !== null && $exp < date('Y-m-d')) { throw new RuntimeException('Il pacchetto selezionato è scaduto.'); } } $isGift = 'N'; } // ------------------------------------------------------------------ // 2b) Controllo anti-duplicato: utente già in questa classe? // ------------------------------------------------------------------ $dup = $pdo->prepare( "SELECT COUNT(*) FROM bookingclass WHERE iduser = :uid AND idserviceschedule = :idschedule AND status != 'cancelled'" ); $dup->execute([ ':uid' => $userid, ':idschedule' => $idserviceschedule, ]); if ((int) $dup->fetchColumn() > 0) { $pdo->rollBack(); header('Location: adminpanel.php?error=duplicate'); exit; } // ------------------------------------------------------------------ // 3) Inserimento prenotazione // ------------------------------------------------------------------ $insBooking = $pdo->prepare( "INSERT INTO bookingclass (iduser, idserviceschedule, status, idorder, idservice, bookingstart, is_gift) VALUES (:iduser, :idschedule, :status, :idorder, :idservice, :bookingstart, :isgift)" ); $insBooking->execute([ ':iduser' => $userid, ':idschedule' => $idserviceschedule, ':status' => $status, ':idorder' => $idorder, // NULL o id reale, mai 0 ':idservice' => $idservice, ':bookingstart' => $bookingstart !== '' ? $bookingstart : null, ':isgift' => $isGift, ]); $pdo->commit(); header('Location: adminpanel.php?success=added'); exit; } catch (Throwable $ex) { if ($pdo->inTransaction()) { $pdo->rollBack(); } error_log('inserisci_record error: ' . $ex->getMessage()); header('Location: adminpanel.php?error=insert'); exit; }