149 lines
4.8 KiB
PHP
149 lines
4.8 KiB
PHP
<?php
|
|
|
|
/**
|
|
* reprogramclass.php
|
|
*
|
|
* Sposta una prenotazione esistente su una nuova classe schedulata.
|
|
* La vecchia collocazione non viene duplicata: la riga di bookingclass
|
|
* viene aggiornata in place, conservando classe/data precedente nei
|
|
* campi idprevserviceschedule / prevbookingstart.
|
|
*
|
|
* Input (POST):
|
|
* - idbookingclass : int prenotazione da spostare
|
|
* - idserviceschedule : int nuova classe destinazione
|
|
* - is_reprogrammed : 'Y'|'N' se 'Y' incrementa orderbook.reprogrammed
|
|
*
|
|
* Regole:
|
|
* - status resta 'booked'
|
|
* - lostlesson NON viene toccato
|
|
* - is_reprogrammed sulla prenotazione va sempre a 'Y'
|
|
* - orderbook.reprogrammed +1 solo se il flag del modale è attivo e c'e un idorder valido
|
|
*
|
|
* Nota: include direttamente class/db-functions.php (dove sta DBHandlerSelect)
|
|
* invece di headscript.php, cosi non viene emesso output HTML prima del JSON.
|
|
*/
|
|
|
|
require_once('class/db-functions.php');
|
|
|
|
header('Content-Type: application/json; charset=utf-8');
|
|
|
|
function fail(string $msg, int $http = 400): void
|
|
{
|
|
http_response_code($http);
|
|
echo json_encode(['error' => $msg]);
|
|
exit;
|
|
}
|
|
|
|
$idbookingclass = isset($_POST['idbookingclass']) ? (int) $_POST['idbookingclass'] : 0;
|
|
$idnewschedule = isset($_POST['idserviceschedule']) ? (int) $_POST['idserviceschedule'] : 0;
|
|
$flagReprogrammed = (isset($_POST['is_reprogrammed']) && $_POST['is_reprogrammed'] === 'Y') ? 'Y' : 'N';
|
|
|
|
if ($idbookingclass <= 0 || $idnewschedule <= 0) {
|
|
fail('Dati mancanti per la riprogrammazione.');
|
|
}
|
|
|
|
$pdo = DBHandlerSelect::getInstance()->getConnection();
|
|
|
|
try {
|
|
$pdo->beginTransaction();
|
|
|
|
// Prenotazione corrente (lock per evitare doppie riprogrammazioni concorrenti)
|
|
$stmt = $pdo->prepare(
|
|
"SELECT idbookingclass, idserviceschedule, bookingstart, idorder, iduser
|
|
FROM bookingclass
|
|
WHERE idbookingclass = :id
|
|
FOR UPDATE"
|
|
);
|
|
$stmt->execute([':id' => $idbookingclass]);
|
|
$booking = $stmt->fetch();
|
|
|
|
if (!$booking) {
|
|
$pdo->rollBack();
|
|
fail('Prenotazione non trovata.', 404);
|
|
}
|
|
|
|
// Classe destinazione
|
|
$stmt = $pdo->prepare(
|
|
"SELECT idserviceschedule, idservice, dateschedule
|
|
FROM serviceschedule
|
|
WHERE idserviceschedule = :id"
|
|
);
|
|
$stmt->execute([':id' => $idnewschedule]);
|
|
$newSchedule = $stmt->fetch();
|
|
|
|
if (!$newSchedule) {
|
|
$pdo->rollBack();
|
|
fail('Classe di destinazione non trovata.', 404);
|
|
}
|
|
|
|
// Nessun senso spostare sulla stessa classe
|
|
if ((int) $booking['idserviceschedule'] === $idnewschedule) {
|
|
$pdo->rollBack();
|
|
fail('La classe di destinazione coincide con quella attuale.');
|
|
}
|
|
|
|
// Anti-duplicato: l'utente e gia prenotato (attivo) nella classe destinazione?
|
|
$dupStmt = $pdo->prepare(
|
|
"SELECT COUNT(*)
|
|
FROM bookingclass
|
|
WHERE idserviceschedule = :newsched
|
|
AND iduser = :iduser
|
|
AND status = 'booked'
|
|
AND idbookingclass <> :id"
|
|
);
|
|
$dupStmt->execute([
|
|
':newsched' => $idnewschedule,
|
|
':iduser' => (int) $booking['iduser'],
|
|
':id' => $idbookingclass,
|
|
]);
|
|
if ((int) $dupStmt->fetchColumn() > 0) {
|
|
$pdo->rollBack();
|
|
fail('L\'allieva e gia prenotata in questa classe.', 409);
|
|
}
|
|
|
|
// Valori precedenti da conservare
|
|
$prevSchedule = $booking['idserviceschedule']; // puo essere NULL
|
|
$prevStart = $booking['bookingstart'];
|
|
|
|
// Aggiorna la prenotazione in place
|
|
$upd = $pdo->prepare(
|
|
"UPDATE bookingclass SET
|
|
idserviceschedule = :newsched,
|
|
idservice = :newservice,
|
|
bookingstart = :newstart,
|
|
idprevserviceschedule = :prevsched,
|
|
prevbookingstart = :prevstart,
|
|
is_reprogrammed = 'Y',
|
|
status = 'booked'
|
|
WHERE idbookingclass = :id"
|
|
);
|
|
$upd->execute([
|
|
':newsched' => $newSchedule['idserviceschedule'],
|
|
':newservice' => $newSchedule['idservice'],
|
|
':newstart' => $newSchedule['dateschedule'],
|
|
':prevsched' => $prevSchedule,
|
|
':prevstart' => $prevStart,
|
|
':id' => $idbookingclass,
|
|
]);
|
|
|
|
// Incrementa il contatore riprogrammazioni sull'ordine, se richiesto e possibile
|
|
$idorder = $booking['idorder'] !== null ? (int) $booking['idorder'] : 0;
|
|
if ($flagReprogrammed === 'Y' && $idorder > 0) {
|
|
$incr = $pdo->prepare(
|
|
"UPDATE orderbook
|
|
SET reprogrammed = reprogrammed + 1
|
|
WHERE idorderbook = :idorder"
|
|
);
|
|
$incr->execute([':idorder' => $idorder]);
|
|
}
|
|
|
|
$pdo->commit();
|
|
|
|
echo json_encode(['success' => true]);
|
|
} catch (Throwable $ex) {
|
|
if ($pdo->inTransaction()) {
|
|
$pdo->rollBack();
|
|
}
|
|
fail('Errore durante la riprogrammazione: ' . $ex->getMessage(), 500);
|
|
}
|