redirection -> GET, après une action sur les accès : un // rafraîchissement de la page ne rejoue jamais l'action) : if (isset($_SESSION['Bateaux']['flash_information'])) { $message_information .= $_SESSION['Bateaux']['flash_information']; unset($_SESSION['Bateaux']['flash_information']); } if (isset($_SESSION['Bateaux']['flash_erreur'])) { $message_erreur .= $_SESSION['Bateaux']['flash_erreur']; unset($_SESSION['Bateaux']['flash_erreur']); } Ouverture_bdd(); // Connexion à MySql //************************************************************************************************************************************ // Traitement des variables d'entrées //************************************************************************************************************************************ // Variables de SESSION : if (!isset($_SESSION['Bateaux']['page'])) $_SESSION['Bateaux']['page'] = 'Accueil'; if (!isset($_SESSION['Bateaux']['ancre'])) $_SESSION['Bateaux']['ancre'] = ""; if (!isset($_SESSION['Bateaux']['origine'])) $_SESSION['Bateaux']['origine'] = ""; if (!isset($_SESSION['Bateaux']['tri_liste'])) $_SESSION['Bateaux']['tri_liste'] = "Flotte"; if (!isset($_SESSION['Bateaux']['sens_tri_liste'])) $_SESSION['Bateaux']['sens_tri_liste'] = "ASC"; if (!isset($_SESSION['Bateaux']['type_details_bateau'])) $_SESSION['Bateaux']['type_details_bateau'] = "resume"; // 'resume' ou 'gerer_les_acces' if (!isset($_SESSION['Bateaux']['bateau']['Cle_primaire'])) $_SESSION['Bateaux']['bateau']['Cle_primaire'] = 0; if (!isset($_SESSION['Bateaux']['bateau']['Nom'])) $_SESSION['Bateaux']['bateau']['Nom'] = ""; if (!isset($_SESSION['Bateaux']['bateau']['ID_Flotte'])) $_SESSION['Bateaux']['bateau']['ID_Flotte'] = 0; if (!isset($_SESSION['Bateaux']['bateau']['Date_mes'])) $_SESSION['Bateaux']['bateau']['Date_mes'] = date("Y-m-d"); if (!isset($_SESSION['Bateaux']['bateau']['Commentaires'])) $_SESSION['Bateaux']['bateau']['Commentaires'] = ""; //--------------------------------------------------------------------------- // Contrôles PRÉALABLES à toute action (synthèse §48) - auparavant, les actions GET et POST s'exécutaient avant tout // contrôle : n'importe quel utilisateur connecté pouvait créer, modifier ou dévalider un bateau. //--------------------------------------------------------------------------- if (!$_SESSION['acces_valide']) { Fermeture_bdd(); header('Location:shipmembers.php?action=navigation&destination=Login'); exit(); } $est_administrateur = ($_SESSION['shipmember']['Niveau_acces'] >= NIVEAU_ACCES_MINI_ADMINISTRATEUR); // Toute requête POST doit porter le jeton de la session (protection contre les formulaires envoyés depuis un autre site, // en complément de SameSite=Lax) : if ($_SERVER['REQUEST_METHOD'] === 'POST' && !Jeton_csrf_valide()) { $_SESSION['Bateaux']['flash_erreur'] = t("Formulaire expiré ou invalide : merci de recommencer."); Fermeture_bdd(); header('Location: bateaux.php'); exit(); } // Gestion de la flotte (liste, création, modification, dévalidation d'un bateau) : réservée aux administrateurs : $actions_flotte = array('tri_liste', 'creation_bateau', 'modification_bateau', 'demande_suppression_bateau'); if (!$est_administrateur && ((isset($_GET['action']) && in_array($_GET['action'], $actions_flotte, true)) || isset($_POST['validation_creation_bateau']) || isset($_POST['validation_modification_bateau']) || isset($_POST['confirmation_suppression_bateau']))) { $_SESSION['Bateaux']['flash_erreur'] = t("Action réservée aux administrateurs."); Fermeture_bdd(); header('Location: bateaux.php'); exit(); } // Variables GET : if (isset($_GET['ancre'])) $_SESSION['Bateaux']['ancre'] = $_GET['ancre']; if (isset($_GET['action'])) { switch ($_GET['action']) { //=================================== case "navigation": { // Seules les pages consultables par simple navigation ; création, modification et suppression passent par leurs // actions dédiées (contrôlées ci-dessus) : if (isset($_GET['destination']) && in_array($_GET['destination'], array('Accueil', 'Details_bateau'), true)) { $_SESSION['Bateaux']['page'] = $_GET['destination']; } if (isset($_GET['ancre'])) { $_SESSION['Bateaux']['ancre'] = $_GET['ancre']; } break; } //=================================== case "changement_langue": { if (isset($_GET['langue'])) { $_SESSION['langue'] = $_GET['langue']; chargement_langue(); } break; } //=================================== case "tri_liste": { if (isset($_GET['colonne'])) { if ($_SESSION['Bateaux']['tri_liste'] == $_GET['colonne']) { if ($_SESSION['Bateaux']['sens_tri_liste'] == "ASC") $_SESSION['Bateaux']['sens_tri_liste'] = "DESC"; else $_SESSION['Bateaux']['sens_tri_liste'] = "ASC"; } else { $_SESSION['Bateaux']['tri_liste'] = $_GET['colonne']; $_SESSION['Bateaux']['sens_tri_liste'] = "ASC"; } } break; } //=================================== case "details_bateau": { if (isset($_GET['id_bateau'])) { $_SESSION['Bateaux']['bateau']['Cle_primaire'] = (int)$_GET['id_bateau']; $_SESSION['Bateaux']['type_details_bateau'] = "resume"; $_SESSION['Bateaux']['generation'] = 0; // Nouveau bateau : génération active $_SESSION['Bateaux']['page'] = "Details_bateau"; if (isset($_GET['origine'])) $_SESSION['Bateaux']['origine'] = $_GET['origine']; else $_SESSION['Bateaux']['origine'] = ""; } break; } //=================================== case "type_details_bateau": { if (isset($_GET['type']) && in_array($_GET['type'], array('resume', 'gerer_les_acces'), true)) $_SESSION['Bateaux']['type_details_bateau'] = $_GET['type']; $_SESSION['Bateaux']['ancre'] = ""; break; } //=================================== // Génération consultée (synthèse §50) : 0 = génération active. La valeur n'est utilisée qu'après vérification // qu'elle appartient bien au bateau affiché (préparation de la page). case "choix_generation": { $_SESSION['Bateaux']['generation'] = isset($_GET['generation']) ? (int)$_GET['generation'] : 0; $_SESSION['Bateaux']['type_details_bateau'] = "resume"; break; } //=================================== case "modification_bateau": { if (isset($_GET['id_bateau'])) { $_SESSION['Bateaux']['bateau']['Cle_primaire'] = (int)$_GET['id_bateau']; $_SESSION['Bateaux']['page'] = "Modification_bateau"; $_SESSION['Bateaux']['charger_bateau'] = true; // Valeurs lues en base à l'affichage du formulaire } break; } //=================================== case "creation_bateau": { $_SESSION['Bateaux']['page'] = "Creation_bateau"; // Formulaire vierge - réinitialisé ICI et non plus à chaque affichage : après une erreur de saisie, le formulaire // réaffiché garde les valeurs saisies : $_SESSION['Bateaux']['bateau'] = array('Cle_primaire' => 0, 'Nom' => "", 'ID_Flotte' => 0, 'Date_mes' => date("Y-m-d"), 'Commentaires' => ""); break; } //=================================== case "demande_suppression_bateau": { if (isset($_GET['id_bateau'])) { $_SESSION['Bateaux']['bateau']['Cle_primaire'] = (int)$_GET['id_bateau']; $_SESSION['Bateaux']['page'] = "Confirmation_suppression_bateau"; } break; } // NB : la confirmation de suppression n'est plus une action GET (un simple lien suffisait à dévalider un bateau) : // elle est envoyée en POST, avec le jeton de session (voir plus bas). } Fermeture_bdd(); if ($_SESSION['Bateaux']['ancre'] == "") header('Location:bateaux.php'); // Permet de "vider" la barre d'URL des champs GET et donc de doubler le traitement en cas de raffraichissement de page... else header('Location:bateaux.php#'.$_SESSION['Bateaux']['ancre'].''); exit(); } // Variables POST : //--------------------------------------------------------------------------- // Création/Modification Bateau (administrateurs - contrôlé plus haut) : // NB : l'affectation d'un module ShipBase à un bateau ne se fait plus ici mais via TB_Affectations_bateaux // (administration de la flotte, lot 4 - synthèse §44.10). Les anciens champs ID_Carte/Date_carte et les // répertoires download/upload/archives du modèle CM4 ont été retirés (synthèse §47). // Valeurs enregistrées TELLES QUELLES (requêtes préparées) : l'ancien addslashes() les stockait avec des barres // obliques (d\'Artagnan), retirées ensuite à l'affichage par stripcslashes() (synthèse §48). if (isset($_POST['validation_creation_bateau']) OR isset($_POST['validation_modification_bateau'])) { // Mémorisation des valeurs saisies pour les réafficher en cas d'erreur : $_SESSION['Bateaux']['bateau']['Nom'] = trim((string)($_POST['Nom'] ?? "")); $_SESSION['Bateaux']['bateau']['ID_Flotte'] = (int)($_POST['ID_Flotte'] ?? 0); $_SESSION['Bateaux']['bateau']['Date_mes'] = trim((string)($_POST['Date_mes'] ?? "")); $_SESSION['Bateaux']['bateau']['Commentaires'] = (string)($_POST['Commentaires'] ?? ""); // Vérifications : $longueur_nom = mb_strlen($_SESSION['Bateaux']['bateau']['Nom']); if ($longueur_nom < 1 || $longueur_nom > 50) $message_erreur .= t("Le nom du bateau doit comporter de 1 à 50 caractères.")."
"; $date = date_create_from_format('!Y-m-d', $_SESSION['Bateaux']['bateau']['Date_mes']); if ($date === false || $date->format('Y-m-d') !== $_SESSION['Bateaux']['bateau']['Date_mes']) $message_erreur .= t("Date de mise en service invalide (format AAAA-MM-JJ).")."
"; if ($_SESSION['Bateaux']['bateau']['ID_Flotte'] != 0) { $reponse = Requete_preparee_bdd("SELECT COUNT(*) AS nb FROM TB_Flottes WHERE Cle_primaire=? AND Validite=1", array(array('i', $_SESSION['Bateaux']['bateau']['ID_Flotte'])), __FILE__, __LINE__); $donnees = Recherche_ligne_bdd($reponse); Liberation_jeu_de_resultat_bdd($reponse); if ($donnees['nb'] == 0) $message_erreur .= t("Flotte inconnue.")."
"; } if ($message_erreur == "") // Sinon : le formulaire est réaffiché avec les valeurs saisies et le message d'erreur { if (isset($_POST['validation_creation_bateau'])) { $requete = 'INSERT INTO TB_Bateaux (Nom, ID_Flotte, Date_mes, Commentaires) VALUES (?, ?, ?, ?)'; Requete_preparee_bdd($requete, array( array('s', $_SESSION['Bateaux']['bateau']['Nom']), array('i', $_SESSION['Bateaux']['bateau']['ID_Flotte']), array('s', $_SESSION['Bateaux']['bateau']['Date_mes']), array('s', $_SESSION['Bateaux']['bateau']['Commentaires'])), __FILE__, __LINE__); $_SESSION['Bateaux']['bateau']['Cle_primaire'] = Recuperation_id_cree_bdd(); $_SESSION['Bateaux']['flash_information'] = str_replace("[[Nom]]", htmlspecialchars($_SESSION['Bateaux']['bateau']['Nom']), t("Le bateau [[Nom]] vient d'être créé.")); } else { $requete = 'UPDATE TB_Bateaux SET Nom=?, ID_Flotte=?, Date_mes=?, Commentaires=? WHERE Cle_primaire=? AND Validite=1'; Requete_preparee_bdd($requete, array( array('s', $_SESSION['Bateaux']['bateau']['Nom']), array('i', $_SESSION['Bateaux']['bateau']['ID_Flotte']), array('s', $_SESSION['Bateaux']['bateau']['Date_mes']), array('s', $_SESSION['Bateaux']['bateau']['Commentaires']), array('i', $_SESSION['Bateaux']['bateau']['Cle_primaire'])), __FILE__, __LINE__); $_SESSION['Bateaux']['flash_information'] = str_replace("[[Nom]]", htmlspecialchars($_SESSION['Bateaux']['bateau']['Nom']), t("Le bateau [[Nom]] vient d'être modifié.")); } $_SESSION['Bateaux']['page'] = "Accueil"; Fermeture_bdd(); header('Location: bateaux.php'); exit(); } } //--------------------------------------------------------------------------- // Dévalidation d'un bateau (administrateurs - contrôlé plus haut ; POST avec jeton) : if (isset($_POST['confirmation_suppression_bateau'])) { $id_bateau = (int)$_POST['confirmation_suppression_bateau']; Requete_preparee_bdd('UPDATE TB_Bateaux SET Validite=0 WHERE Cle_primaire=? AND Validite=1', array(array('i', $id_bateau)), __FILE__, __LINE__); if (Nb_lignes_modifiees() == 1) $_SESSION['Bateaux']['flash_information'] = t("Le bateau a été dévalidé dans la base de données."); else $_SESSION['Bateaux']['flash_erreur'] = t("Ce bateau n'existe pas ou a déjà été dévalidé."); $_SESSION['Bateaux']['page'] = "Accueil"; Fermeture_bdd(); header('Location: bateaux.php'); exit(); } //--------------------------------------------------------------------------- // NB : les actions sur les accès et invitations (création, suspension, réactivation, révocation, modification, PDF) // sont traitées plus bas, dans la page Details_bateau, APRÈS le calcul des droits de l'utilisateur sur le bateau // (elles étaient auparavant exécutées ici, avant tout contrôle - synthèse §47). //************************************************************************************************************************************ // Traitement des données //************************************************************************************************************************************ // Protection contre les accès directs... : $flag_sortie = true; do // Dummy loop : { if (!$_SESSION['acces_valide']) break; // Si on n'est pas identifié, on ne peut pas accéder quoi qu'il arrive... if ($_SESSION['shipmember']['Niveau_acces'] >= NIVEAU_ACCES_MINI_ADMINISTRATEUR) { $flag_sortie = false; // Si on est administrateur, on a toujours accès.... break; } // Recherche des droits d'accès à un bateau en particulier : if ($_SESSION['Bateaux']['page'] == "Details_bateau") { $requete = "SELECT * FROM TB_Lien_bateau_shipmember WHERE Statut='actif' AND Fin_validite >= NOW() AND ID_SHIPMEMBER=? AND ID_BATEAU=? "; $reponse = Requete_preparee_bdd($requete, array( array('i', $_SESSION['shipmember']['Cle_primaire']), array('i', $_SESSION['Bateaux']['bateau']['Cle_primaire'])), __FILE__, __LINE__); while ($donnees = Recherche_ligne_bdd($reponse)) { $flag_sortie = false; break; } Liberation_jeu_de_resultat_bdd($reponse); } } while (0); if ($flag_sortie) { // exit indispensable : sans lui, le reste de la page (actions comprises) s'exécutait malgré la redirection (synthèse §47) Fermeture_bdd(); header('Location:shipmembers.php?action=navigation&destination=Login'); exit(); } switch ($_SESSION['Bateaux']['page']) { //**************************************************************************************************************************** case "Accueil": { //-------------------------------------------------- // Récupération des informations sur les bateaux : $nb_bateaux = 0; switch($_SESSION['Bateaux']['tri_liste']) { case "Nom": { $tri_liste = " ORDER By Nom ".$_SESSION['Bateaux']['sens_tri_liste']; break; } case "Flotte" : { $tri_liste = " ORDER By nom_flotte ".$_SESSION['Bateaux']['sens_tri_liste'].", Nom"; break; } case "Adresse_mac": { $tri_liste = " ORDER By adresse_carte ".$_SESSION['Bateaux']['sens_tri_liste']; break; } case "Version": { $tri_liste = " ORDER By version ".$_SESSION['Bateaux']['sens_tri_liste'].", Nom"; break; } case "Date_maj": { $tri_liste = " ORDER By Date_derniere_maj ".$_SESSION['Bateaux']['sens_tri_liste'].", Nom"; break; } default : { $tri_liste = " ORDER By nom_flotte, Nom ".$_SESSION['Bateaux']['sens_tri_liste']; break; } } $requete = 'SELECT TB_Bateaux.Cle_primaire AS Cle_primaire, '; $requete .= ' TB_Bateaux.Nom AS Nom, '; $requete .= ' (SELECT Nom FROM TB_Flottes WHERE Validite=1 AND Cle_primaire=TB_Bateaux.ID_Flotte) AS nom_flotte, '; $requete .= ' (SELECT Adresse_mac FROM TB_Affectations_bateaux WHERE ID_Bateau=TB_Bateaux.Cle_primaire AND Date_fin IS NULL) AS adresse_carte, '; $requete .= ' (SELECT Version_soft FROM TB_Generations_bateaux WHERE ID_Bateau=TB_Bateaux.Cle_primaire AND Date_fin IS NULL) AS version, '; $requete .= ' TB_Bateaux.Date_derniere_maj AS Date_derniere_maj, '; $requete .= ' TB_Bateaux.Commentaires AS Commentaires '; $requete .= ' FROM `TB_Bateaux` '; $requete .= ' WHERE Validite=1 '; $requete .= $tri_liste; //echo "Requête = [ ".$requete."; ]
"; $reponse = Requete_preparee_bdd($requete, array(), __FILE__, __LINE__); while ($donnees = Recherche_ligne_bdd($reponse)) { $bateaux[$nb_bateaux] = $donnees; // Mise en forme de certaines variables : $bateaux[$nb_bateaux]['version'] = ($donnees['version'] == "") ? 'inconnue' : htmlspecialchars($donnees['version']); if ($donnees['Date_derniere_maj'] < "2020-01-02") $bateaux[$nb_bateaux]['Date_derniere_maj'] = "Jamais"; else $bateaux[$nb_bateaux]['Date_derniere_maj'] = ''.htmlspecialchars($donnees['Date_derniere_maj']).' UTC'; $nb_bateaux ++; } Liberation_jeu_de_resultat_bdd($reponse); break; } //**************************************************************************************************************************** case "Details_bateau": { //-------------------------------------------------- // Récupération des informations sur le bateau : $nb_bateaux = 0; $requete = 'SELECT *, '; $requete .= ' (SELECT Adresse_mac FROM TB_Affectations_bateaux WHERE ID_Bateau=TB_Bateaux.Cle_primaire AND Date_fin IS NULL) AS Adresse_mac, '; $requete .= ' (SELECT Version_soft FROM TB_Generations_bateaux WHERE ID_Bateau=TB_Bateaux.Cle_primaire AND Date_fin IS NULL) AS version, '; // Adresse NetBird du module affecté (Live distant possible seulement si elle est connue - synthèse §49) : $requete .= ' (SELECT C.Adresse_netbird FROM TB_Affectations_bateaux A JOIN TB_Cartes C ON C.Adresse_mac=A.Adresse_mac WHERE A.ID_Bateau=TB_Bateaux.Cle_primaire AND A.Date_fin IS NULL) AS Adresse_netbird '; $requete .= ' FROM TB_Bateaux WHERE Cle_primaire=? '; //echo "Requête = [ ".$requete."; ]
"; $reponse = Requete_preparee_bdd($requete, array( array('i', $_SESSION['Bateaux']['bateau']['Cle_primaire'])), __FILE__, __LINE__); while ($donnees = Recherche_ligne_bdd($reponse)) { $bateau = $donnees; $bateau['Date_derniere_maj_utc'] = $donnees['Date_derniere_maj']; // Brute (UTC), pour l'indicateur de fraîcheur // Mise en forme de textes : if ($donnees['Date_derniere_maj'] < "2020-01-02") $bateau['Date_derniere_maj'] = "".t("Jamais").""; else { $bateau['Date_derniere_maj'] = Formatage_date($donnees['Date_derniere_maj']); $_SESSION['Bateaux']['derniere_maj'] = $donnees['Date_derniere_maj']; } // $bateau['Commentaires'] = htmlspecialchars(stripcslashes($bateau['Commentaires'])); } Liberation_jeu_de_resultat_bdd($reponse); //--------------------------------------------- // Recherche des droits d'accès au bateau : //--------------------------------------------- if ($_SESSION['shipmember']['Niveau_acces'] >= NIVEAU_ACCES_MINI_ADMINISTRATEUR) // Dans le cas des administrateurs, on accorde tous les droits, indépendamment des paramètres du bateau { $acces_profil['Creation_profils'] = 1; $acces_profil['Devalidation_profils'] = 2; $acces_profil['Consultation_donnees'] = 2; $acces_profil['Modification_acces'] = 1; } else { // Valeurs par défaut : $id_type_acces = 0; $acces_profil['Creation_profils'] = 0; $acces_profil['Devalidation_profils'] = 0; $acces_profil['Consultation_donnees'] = 0; $acces_profil['Modification_acces'] = 0; // Recherche de l'ID de l'accès le plus élevé pour ce bateau et ce shipmember : // NB : "ORDER BY ... ASC" - plus la clé du type est petite, plus il donne de droits (2 Propriétaire, 3 Installateur, // 4 Skipper). L'ancien "DESC" retenait l'accès le plus FAIBLE quand un SM en avait plusieurs (synthèse §47). $requete = "SELECT ID_Type_acces_bateau_shipmember FROM TB_Lien_bateau_shipmember WHERE Statut='actif' AND ID_Shipmember=? AND ID_Bateau=? AND Fin_validite>=? ORDER BY ID_Type_acces_bateau_shipmember ASC LIMIT 1"; $reponse = Requete_preparee_bdd($requete, array( array('i', $_SESSION['shipmember']['Cle_primaire']), array('i', $_SESSION['Bateaux']['bateau']['Cle_primaire']), array('s', date_format(date_create(), 'Y-m-d H:i:s'))), __FILE__, __LINE__); while ($donnees = Recherche_ligne_bdd($reponse)) { $id_type_acces = $donnees['ID_Type_acces_bateau_shipmember']; } Liberation_jeu_de_resultat_bdd($reponse); // Recherche des caractérirtiques de l'accès le plus élevé trouvé : if ($id_type_acces > 0) { $requete = 'SELECT * FROM TB_Types_acces_bateau_shipmember WHERE Validite=1 AND Cle_primaire=?'; $reponse = Requete_preparee_bdd($requete, array( array('i', $id_type_acces)), __FILE__, __LINE__); while ($donnees = Recherche_ligne_bdd($reponse)) { $acces_profil = $donnees; } Liberation_jeu_de_resultat_bdd($reponse); } $acces_profil['Modification_acces'] = 0; // Modification d'un accès (type, fin) : réservée aux administrateurs } // Récupération des types d'accès possibles : $requete = 'SELECT * FROM TB_Types_acces_bateau_shipmember WHERE Validite=1 '; $reponse = Requete_bdd($requete, __FILE__, __LINE__); $type_acces_nb = 0; while($donnees = Recherche_ligne_bdd($reponse)){ if ($_SESSION['langue'] == "EN") $donnees['Nom'] = $donnees['Nom_en']; else $donnees['Nom'] = $donnees['Nom_fr']; $type_acces[$type_acces_nb++] = $donnees; } Liberation_jeu_de_resultat_bdd($reponse); //------------------------------------------------------------------------------------------------------------ // Actions sur les accès et invitations de CE bateau (synthèse §47). Traitées ici, APRÈS le calcul des droits : // - chaque action vérifie que l'accès visé appartient bien au bateau affiché ; // - créer une invitation, télécharger son PDF : administrateur, ou Creation_profils = 1 ; // - suspendre, réactiver, révoquer : administrateur, ou Devalidation_profils = 2 (tous types), ou = 1 (tous // sauf Propriétaire) ; une invitation en attente peut aussi être révoquée par qui peut en créer ; // - modifier le type ou la fin d'un accès : administrateur. // Après chaque action : redirection vers la page (motif POST -> redirection -> GET). //------------------------------------------------------------------------------------------------------------ $est_administrateur = ($_SESSION['shipmember']['Niveau_acces'] >= NIVEAU_ACCES_MINI_ADMINISTRATEUR); $peut_inviter = ($est_administrateur || $acces_profil['Creation_profils'] == 1); //------------------------------------------------------------------------------------------------------------ // Live distant (synthèse §49) : création d'un ticket (aléatoire, 60 s, usage unique, lié à l'utilisateur et au // bateau) puis redirection vers https://b.ship2net.fr/_auth?ticket=... - le vérificateur du VPS l'échange // contre une session (cookie propre au sous-domaine du bateau). Seule l'empreinte du ticket est enregistrée. // Droit : arriver jusqu'ici suffit (administrateur, ou accès actif à CE bateau - contrôlé plus haut) ; le // vérificateur revérifie de toute façon à l'ouverture de la session puis à chaque requête. $live_possible = ($bateau['Adresse_netbird'] ?? '') != ''; if (isset($_POST['ouvrir_live'])) { if (!$live_possible) { $_SESSION['Bateaux']['flash_erreur'] = t("Aucun module ShipBase joignable n'est affecté à ce bateau : le Live est indisponible."); Fermeture_bdd(); header('Location: bateaux.php'); exit(); } $ticket = bin2hex(random_bytes(32)); Requete_preparee_bdd("INSERT INTO TB_Tickets_live (Empreinte, ID_Shipmember, ID_Bateau, Expiration) VALUES (?, ?, ?, NOW() + INTERVAL 60 SECOND)", array(array('s', hash('sha256', $ticket)), array('i', $_SESSION['shipmember']['Cle_primaire']), array('i', $bateau['Cle_primaire'])), __FILE__, __LINE__); Fermeture_bdd(); header('Location: https://b'.(int)$bateau['Cle_primaire'].'.'.URL_SITE.'/_auth?ticket='.$ticket, true, 303); exit(); } if (isset($_POST['creer_invitation'])) { if (!$peut_inviter) $_SESSION['Bateaux']['flash_erreur'] = t("Vous n'avez pas le droit d'inviter sur ce bateau."); else { $resultat = Creer_invitation($bateau['Cle_primaire'], $_POST['email_invite'] ?? '', $_POST['prenom_invite'] ?? '', $_POST['nom_invite'] ?? '', (int)($_POST['type_acces'] ?? 0), $_POST['fin_acces'] ?? '', $_SESSION['shipmember']['Cle_primaire']); if ($resultat['ok']) $_SESSION['Bateaux']['flash_information'] = str_replace("[[Code]]", $resultat['code'], t("Invitation créée (code [[Code]]). Téléchargez son PDF dans la liste ci-dessous.")); else $_SESSION['Bateaux']['flash_erreur'] = $resultat['raison']; } Fermeture_bdd(); header('Location: bateaux.php'); exit(); } if (isset($_POST['action_acces']) && isset($_POST['ID'])) { $lien = Lien_du_bateau((int)$_POST['ID'], $bateau['Cle_primaire']); $action = (string)$_POST['action_acces']; if ($lien === null) $_SESSION['Bateaux']['flash_erreur'] = t("Accès introuvable pour ce bateau."); else if ($action == 'pdf') { if (!$peut_inviter || $lien['Statut'] != 'en_attente') $_SESSION['Bateaux']['flash_erreur'] = t("Action non autorisée."); else { $invitation = Invitation_par_code($lien['Code']); $invitation['Code'] = $lien['Code']; $invitation['Expiration_invitation'] = $lien['Expiration_invitation']; Fermeture_bdd(); code_acces_pdf($invitation); exit(); } } else { $autorise = Peut_devalider_acces($acces_profil, $est_administrateur, $lien['ID_Type_acces_bateau_shipmember']) || ($action == 'revoquer' && $lien['Statut'] == 'en_attente' && $peut_inviter); $transitions = array( 'suspendre' => array("'actif'", 'suspendu'), 'reactiver' => array("'suspendu'", 'actif'), 'revoquer' => array("'en_attente','actif','suspendu'", 'revoque')); if (!$autorise || !isset($transitions[$action])) $_SESSION['Bateaux']['flash_erreur'] = t("Action non autorisée."); else { $requete = "UPDATE TB_Lien_bateau_shipmember SET Statut=? WHERE ID=? AND ID_Bateau=? AND Statut IN (".$transitions[$action][0].")"; Requete_preparee_bdd($requete, array( array('s', $transitions[$action][1]), array('i', $lien['ID']), array('i', $bateau['Cle_primaire'])), __FILE__, __LINE__); if (Nb_lignes_modifiees() == 1) $_SESSION['Bateaux']['flash_information'] = t("Accès mis à jour."); else $_SESSION['Bateaux']['flash_erreur'] = t("Cet accès a déjà changé d'état."); } } Fermeture_bdd(); header('Location: bateaux.php'); exit(); } if (isset($_POST['modifierAcces']) && isset($_POST['ID'])) { $lien = Lien_du_bateau((int)$_POST['ID'], $bateau['Cle_primaire']); $date = date_create_from_format('Y-m-d', (string)($_POST['fin_validite'] ?? '')); if (!$est_administrateur || $lien === null || $lien['Statut'] == 'revoque') $_SESSION['Bateaux']['flash_erreur'] = t("Action non autorisée."); else if ($date === false) $_SESSION['Bateaux']['flash_erreur'] = t("Date de fin d'accès invalide."); else { $requete = "UPDATE TB_Lien_bateau_shipmember SET Fin_validite=?, ID_Type_acces_bateau_shipmember=? WHERE ID=? AND ID_Bateau=? AND EXISTS (SELECT 1 FROM TB_Types_acces_bateau_shipmember WHERE Cle_primaire=? AND Validite=1)"; Requete_preparee_bdd($requete, array( array('s', $date->format('Y-m-d').' 23:59:59'), array('i', (int)$_POST['type_profil']), array('i', $lien['ID']), array('i', $bateau['Cle_primaire']), array('i', (int)$_POST['type_profil'])), __FILE__, __LINE__); if (Nb_lignes_modifiees() == 1) $_SESSION['Bateaux']['flash_information'] = t("Accès mis à jour."); else $_SESSION['Bateaux']['flash_erreur'] = t("Aucune modification enregistrée (type d'accès invalide, ou valeurs identiques)."); } Fermeture_bdd(); header('Location: bateaux.php'); exit(); } //----------------------------------------------------------- // Recherche des informations complémentaires sur le bateau : switch($_SESSION['Bateaux']['type_details_bateau']) { //========================= case "gerer_les_acces": { // Accès et invitations du bateau, hors révoqués (synthèse §47) - une seule requête au lieu de 3 par ligne : $colonne_type = ($_SESSION['langue'] == "EN") ? 'Nom_en' : 'Nom_fr'; $requete = "SELECT L.*, S.Prenom AS sm_Prenom, S.Nom AS sm_Nom, S.Email AS sm_Email, C.Prenom AS cree_par_Prenom, C.Nom AS cree_par_Nom, T.".$colonne_type." AS Niveau_acces_nom, (L.Expiration_invitation IS NOT NULL AND L.Expiration_invitation <= NOW()) AS Expiree FROM TB_Lien_bateau_shipmember L LEFT JOIN TB_Shipmembers S ON S.ID = L.ID_Shipmember LEFT JOIN TB_Shipmembers C ON C.ID = L.Cree_par LEFT JOIN TB_Types_acces_bateau_shipmember T ON T.Cle_primaire = L.ID_Type_acces_bateau_shipmember WHERE L.ID_Bateau=? AND L.Statut <> 'revoque' ORDER BY FIELD(L.Statut, 'actif', 'suspendu', 'en_attente'), L.Date_creation"; $reponse = Requete_preparee_bdd($requete, array(array('i', $bateau['Cle_primaire'])), __FILE__, __LINE__); $utilisateur_acces_nb = 0; while ($donnees = Recherche_ligne_bdd($reponse, MYSQLI_ASSOC)) { // Destinataire affiché : le ShipMember s'il a accepté, sinon la personne invitée : if ($donnees['Statut'] == 'en_attente') $donnees['Destinataire'] = trim($donnees['Prenom_invite'].' '.$donnees['Nom_invite']).' ['.$donnees['Email_invite'].']'; else $donnees['Destinataire'] = trim($donnees['sm_Prenom'].' '.$donnees['sm_Nom']).' ['.$donnees['sm_Email'].']'; $donnees['Cree_par_nom'] = trim($donnees['cree_par_Prenom'].' '.$donnees['cree_par_Nom']); unset($donnees['Code']); // Jamais envoyé au navigateur (le JSON de chaque ligne alimente le popup) $utilisateur_acces[$utilisateur_acces_nb++] = $donnees; } Liberation_jeu_de_resultat_bdd($reponse); break; } //------------------------------------------------------------------------------------------------------- // Données du bateau (synthèse §50) : lues dans la base de la génération consultée (active par défaut), par // une connexion dédiée - la connexion principale du site n'est pas touchée. default: { $consultation = array('autorisee' => ($est_administrateur || (int)($acces_profil['Consultation_donnees'] ?? 0) >= 1), 'generations' => array(), 'generation' => null, 'domaines' => array(), 'erreur' => null, 'periode_archivage' => CONSULTATION_PERIODE_ARCHIVAGE_DEFAUT); if (!$consultation['autorisee']) break; $consultation['generations'] = Generations_bateau($bateau['Cle_primaire']); foreach ($consultation['generations'] as $generation) { // Génération demandée si elle appartient bien à ce bateau, sinon la génération active : if ((int)$generation['Cle_primaire'] == (int)($_SESSION['Bateaux']['generation'] ?? 0)) { $consultation['generation'] = $generation; break; } if ($generation['Date_fin'] === null && $consultation['generation'] === null) $consultation['generation'] = $generation; } if ($consultation['generation'] === null) break; // Aucune archive reçue pour ce bateau $db_generation = Connexion_generation($consultation['generation']['Nom_base']); if ($db_generation === null) { $consultation['erreur'] = t("Les données de ce bateau sont momentanément inaccessibles."); break; } $consultation['periode_archivage'] = Periode_archivage_bateau($db_generation); $consultation['alarmes'] = Episodes_alarmes($db_generation, 20); foreach (array('circuits' => t("Circuits"), 'capteurs' => t("Capteurs"), 'batteries' => t("Batteries"), 'reservoirs' => t("Réservoirs")) as $domaine => $titre) { $consultation['domaines'][$domaine] = array('titre' => $titre, 'familles' => Elements_domaine($db_generation, $domaine)); } $db_generation->close(); // Génération active : demande d'archive immédiate (si les données ne sont pas déjà récentes - étape 3d) : $consultation['demande'] = ($consultation['generation']['Date_fin'] === null) ? Demander_archive_si_besoin($bateau['Cle_primaire'], $bateau['Date_derniere_maj_utc']) : null; $consultation['demande_archive'] = (($consultation['demande']['statut'] ?? '') == 'demandee'); break; } } // Fin du switch 'type_details_bateau' break; } //**************************************************************************************************************************** case "Creation_bateau": case "Modification_bateau": { //-------------------------------------------------- // Préparation des variables du bateau. Création : formulaire réinitialisé par l'action "creation_bateau". // Modification : valeurs lues en base à l'ouverture du formulaire seulement (après une erreur de saisie, les // valeurs saisies sont conservées) : if ($_SESSION['Bateaux']['page'] == "Modification_bateau" && !empty($_SESSION['Bateaux']['charger_bateau'])) { unset($_SESSION['Bateaux']['charger_bateau']); $requete = 'SELECT Cle_primaire, Nom, ID_Flotte, Date_mes, Commentaires FROM TB_Bateaux WHERE Cle_primaire=? AND Validite=1'; $reponse = Requete_preparee_bdd($requete, array( array('i', $_SESSION['Bateaux']['bateau']['Cle_primaire'])), __FILE__, __LINE__); $donnees = Recherche_ligne_bdd($reponse); Liberation_jeu_de_resultat_bdd($reponse); if ($donnees) $_SESSION['Bateaux']['bateau'] = $donnees; else $_SESSION['Bateaux']['page'] = "Accueil"; } //-------------------------------------------------- // Recherche des flottes existantes : $nb_flottes = 0; $flottes[$nb_flottes]['Cle_primaire'] = 0; $flottes[$nb_flottes]['Nom'] = '--- Affecté à aucune flotte ---'; $nb_flottes ++; $requete = 'SELECT * FROM TB_Flottes WHERE Validite=1 ORDER BY Nom ASC'; $reponse = Requete_preparee_bdd($requete, array(), __FILE__, __LINE__); while ($donnees = Recherche_ligne_bdd($reponse)) { $flottes[$nb_flottes ++] = $donnees; } Liberation_jeu_de_resultat_bdd($reponse); break; } //**************************************************************************************************************************** case "Confirmation_suppression_bateau": { // Nom du bateau à confirmer, relu en base (auparavant : le dernier nom chargé en session, qui pouvait être celui // d'un AUTRE bateau) : $reponse = Requete_preparee_bdd('SELECT Cle_primaire, Nom FROM TB_Bateaux WHERE Cle_primaire=? AND Validite=1', array(array('i', $_SESSION['Bateaux']['bateau']['Cle_primaire'])), __FILE__, __LINE__); $bateau_a_supprimer = Recherche_ligne_bdd($reponse); Liberation_jeu_de_resultat_bdd($reponse); if (!$bateau_a_supprimer) $_SESSION['Bateaux']['page'] = "Accueil"; break; } //**************************************************************************************************************************** default: { $_SESSION['Bateaux']['page'] = "Accueil"; break; } } Fermeture_bdd(); // Déconnexion de MySQL //************************************************************************************************************************************ // Affichage //************************************************************************************************************************************ Entete_page_html(); //******************************************************************************************************************************** // Affichage principal : echo '
'; //========================================================================================= // Entête : Entete_page($message_erreur, $message_information); switch ($_SESSION['Bateaux']['page']) { //************************************************************************************************************************ case "Accueil": { echo '
'; echo '

Bateaux

'; echo '
'; echo ''; echo ''; echo ''; // echo ''; echo ''; echo ''; echo ''; // echo ''; echo ''; for ($i = 0; $i < $nb_bateaux; $i ++) { echo ''; echo ''; // echo ''; echo ''; echo ''; echo ''; // echo ''; echo ''; } echo '
NomFlotteShipBaseAdresse MACVersion'.t("Dernières données reçues").'Commentaires
'.htmlspecialchars($bateaux[$i]['Nom']).' '.htmlspecialchars((string)$bateaux[$i]['nom_flotte']).''.$bateaux[$i]['nom_carte'].''.htmlspecialchars((string)$bateaux[$i]['adresse_carte']).''.$bateaux[$i]['version'].''.$bateaux[$i]['Date_derniere_maj'].''.$bateaux[$i]['Commentaires'].'
'; echo '
'; echo ''; echo '
'; break; } //**************************************************************************************************************************** case "Details_bateau": { echo '
'; echo '

Bateau '.htmlspecialchars($bateau['Nom']).'

'; echo '
'; if ($_SESSION['shipmember']['Niveau_acces'] >= NIVEAU_ACCES_MINI_ADMINISTRATEUR || $acces_profil['Consultation_donnees'] == 2) { echo ''; } //-------------------------------- // Bouton Live (synthèse §49) - formulaire POST avec jeton (un navigateur qui pré-charge les liens ne crée pas // de tickets), ouvert dans un nouvel onglet : echo '
'; if ($live_possible) { echo '
'.Champ_jeton_csrf(); echo ''; echo '
'; } else echo ''.t("Live indisponible").''; echo '
'; // Indicateur de fraîcheur (synthèse §44.6, §50) : date UTC transmise au navigateur, qui l'affiche dans le fuseau // de l'utilisateur et colore selon l'ancienneté (seuil orange/rouge = 1,25 x la période d'archivage du bateau) : echo '
'.t("Dernières données reçues").' : '; if ($bateau['Date_derniere_maj_utc'] === null || $bateau['Date_derniere_maj_utc'] < "2020-01-02") echo ''.t("Jamais").''; else echo ''.htmlspecialchars($bateau['Date_derniere_maj_utc']).' UTC'; // Mise à jour à l'ouverture (étape 3d) : ce qui a été fait, et pourquoi (synthèse §50) : $minutes = function($secondes) { return max(1, (int)ceil($secondes / 60)); }; switch ($consultation['demande']['statut'] ?? '') { case 'demandee': echo ''.t("Mise à jour demandée au bateau...").''; break; case 'donnees_recentes': echo ''.str_replace("[[M]]", $minutes($consultation['demande']['attente']), t("Données récentes : pas de nouvelle demande au bateau avant [[M]] min.")).''; break; case 'deja_demandee': echo ''.str_replace("[[M]]", $minutes($consultation['demande']['attente']), t("Mise à jour déjà demandée récemment : nouvelle demande possible dans [[M]] min.")).''; break; } echo '
'; echo '
'; //-------------------------------- // Boutons de haut de page (les anciens onglets Carte/Batteries/Circuits/Réservoirs/Capteurs/Système, liés au // modèle CM4 centralisé, ont été retirés - la consultation des données sera refaite sur la base de la génération // active du bateau, lot 3 - synthèse §44.10) : echo '
'; echo '
'; echo ''.t("Données du bateau").''; echo '
'; echo '
'; echo '
'; switch($_SESSION['Bateaux']['type_details_bateau']) { //=========================================================== case "gerer_les_acces": { // Convention (synthèse §48) : les textes traduits (t()) sont affichés tels quels - ils sont écrits dans les // fichiers de langue, pas saisis par les utilisateurs ; seules les DONNÉES (base, saisie) sont échappées. echo '
'; //-------------------------------------------- // Formulaire d'invitation nominative (synthèse §47) : if ($peut_inviter) { echo '
'; echo '

'.t("Inviter une personne sur ce bateau").'

'; echo '
'; echo Champ_jeton_csrf(); echo ' '; echo ' '; echo ' '; echo ' '; echo ' '; echo ' '; echo '
'; echo '
'; } //-------------------------------------------- // Liste des accès et des invitations en attente : echo '
'; echo ' '; echo ' '; echo ' '; echo ' '; echo ' '; echo ' '; echo ' '; echo ' '; echo ' '; if ($utilisateur_acces_nb == 0) echo ''; for ($i = 0; $i < $utilisateur_acces_nb; $i++) { $acces = $utilisateur_acces[$i]; // Statut affiché : switch ($acces['Statut']) { case 'actif': $statut = t("Actif"); $classe_statut = 'actif'; break; case 'suspendu': $statut = t("Suspendu"); $classe_statut = 'suspendu'; break; default: if ($acces['Expiree']) { $statut = t("Invitation expirée"); $classe_statut = 'expiree'; } else { $statut = str_replace("[[Date]]", date_format(date_create($acces['Expiration_invitation']), 'd/m/Y'), t("Invitation en attente (jusqu'au [[Date]])")); $classe_statut = 'en_attente'; } break; } // Actions permises sur cette ligne : $peut_devalider = Peut_devalider_acces($acces_profil, $est_administrateur, $acces['ID_Type_acces_bateau_shipmember']); $actions = array(); if ($acces['Statut'] == 'actif' && $peut_devalider) $actions['suspendre'] = t("Suspendre"); if ($acces['Statut'] == 'suspendu' && $peut_devalider) $actions['reactiver'] = t("Réactiver"); if ($acces['Statut'] == 'en_attente' && !$acces['Expiree'] && $peut_inviter) $actions['pdf'] = t("PDF"); if ($peut_devalider || ($acces['Statut'] == 'en_attente' && $peut_inviter)) $actions['revoquer'] = t("Révoquer"); echo ' '; echo ' '; echo ' '; echo ' '; echo ' '; echo ' '; echo ' '; echo ' '; } echo '
'.t("Statut").''.t("Destinataire").''.t("Créé par").''.t("Type de profil").''.t("Fin de validité").'
'.t("Aucun accès ni invitation en cours.").'
'.$statut.''.htmlspecialchars((string)$acces['Destinataire']).''.htmlspecialchars((string)$acces['Cree_par_nom']).''.htmlspecialchars((string)$acces['Niveau_acces_nom']).''.((substr($acces['Fin_validite'], 0, 10) == "9999-12-31") ? t("Aucune") : date_format(date_create($acces['Fin_validite']), 'd/m/Y')).'
'; if (count($actions) > 0) { echo '
'; echo Champ_jeton_csrf(); echo ''; foreach ($actions as $code_action => $libelle) { echo ' '; } echo '
'; } if ($acces_profil['Modification_acces'] == 1) { echo ''; } echo '
'; echo '
'; echo '
'; // Fin de class="gestion_acces" //-------------------------------------------- // Popup de modification (administrateurs) : type d'accès et fin de validité. // (La suppression se fait désormais par le bouton "Révoquer" de chaque ligne.) if ($acces_profil['Modification_acces'] == 1) { echo ''; } break; } //=========================================================== // 'resume' (et toute ancienne valeur de session) : default: { if (!$consultation['autorisee']) { echo '

'.t("Votre type d'accès ne permet pas de consulter les données de ce bateau.").'

'; break; } if ($consultation['generation'] === null) { echo '

'.t("Aucune donnée n'a encore été reçue de ce bateau.").'

'; break; } if ($consultation['erreur'] !== null) { echo '

'.htmlspecialchars($consultation['erreur']).'

'; break; } echo '
'; // Rafraîchissement à l'arrivée d'une nouvelle archive (synthèse §50) - génération active seulement : if ($consultation['generation']['Date_fin'] === null) { echo ''; } //-------------------------------- // Génération consultée, et choix d'une génération antérieure : $format_date = function($date) { return ($date === null) ? '' : date_format(date_create($date), 'd/m/Y'); }; echo '
'; echo ''; echo ''; echo ''; echo ''; echo '
'; if ($consultation['generation']['Date_fin'] !== null) { echo '

'.t("Vous consultez une génération antérieure : les valeurs ci-dessous sont celles de sa dernière archive, pas l'état actuel du bateau.").'

'; } //-------------------------------- // Dernières alarmes (synthèse §50) : déclenchements, du plus récent au plus ancien, dates dans le fuseau du // navigateur. (Pas d'état "alarme en cours" : vieux de jusqu'à une période d'archivage, il ne serait ni // fiable ni exploitable.) echo '
'; echo '

'.t("Dernières alarmes").'

'; if (count($consultation['alarmes'] ?? array()) == 0) echo '

'.t("Aucune alarme enregistrée.").'

'; else { $date_affichee = function($iso) { return ''.htmlspecialchars($iso).''; }; echo ''; echo ''; foreach ($consultation['alarmes'] as $alarme) { switch ($alarme['statut']) { case 'termine': $fin = $date_affichee($alarme['fin_utc']); break; case 'en_cours': $fin = ''.t("en cours à la dernière archive").''; break; case 'fin_non_enregistree': $fin = ''.t("fin non enregistrée").''; break; case 'debut_anterieur': $fin = $date_affichee($alarme['fin_utc']); break; default: $fin = ''.t("ponctuel").''; break; } echo ''; echo ''; echo ''; echo ''; echo ''; echo ''; echo ''; } echo '
'.t("Début").''.t("Fin").''.t("Durée").''.t("Alarme").'
'.(($alarme['debut_utc'] !== null) ? $date_affichee($alarme['debut_utc']) : ''.t("début antérieur").'').''.$fin.''.(($alarme['duree'] !== null) ? htmlspecialchars(Duree_lisible($alarme['duree'])) : '').''.htmlspecialchars($alarme['nom']).''.htmlspecialchars($alarme['message']).'
'; } echo '
'; //-------------------------------- // Les quatre domaines, par famille, avec leurs dernières valeurs : foreach ($consultation['domaines'] as $domaine => $donnees_domaine) { if (count($donnees_domaine['familles']) == 0) continue; echo '
'; echo '

'.htmlspecialchars($donnees_domaine['titre']).'

'; foreach ($donnees_domaine['familles'] as $famille) { echo '
'; echo '

'.htmlspecialchars($famille['nom']).'

'; echo ''; foreach ($famille['elements'] as $element) { // Élément avec courbe historique : ligne cliquable (synthèse §50, étape 3c) $classes = array(); if ($element['defaut'] !== null) $classes[] = 'en_defaut'; if ($element['courbe']) $classes[] = 'avec_courbe'; echo ' 0) ? ' class="'.implode(' ', $classes).'"' : '') .($element['courbe'] ? ' data-type="'.$domaine.'" data-element="'.(int)$element['id'].'" data-nom="'.htmlspecialchars($element['nom']).'" title="'.t("Afficher la courbe").'"' : '').'>'; echo ''; echo ''; echo ''; echo ''; } echo '
'.htmlspecialchars($element['nom']).''.htmlspecialchars(implode(' ', $element['valeurs'])).''.(($element['defaut'] !== null) ? htmlspecialchars($element['defaut']) : '').'
'; echo '
'; } echo '
'; } //-------------------------------- // Panneau de courbe historique (synthèse §50, étape 3c), ouvert au clic sur un élément : echo ''; echo ''; echo '
'; // Fin de class="consultation" break; } } echo '
'; // Fin de class="corps_details_bateau" //-------------------------------- echo '
'; if ($_SESSION['Bateaux']['origine'] == "shipmember") echo 'Retour au menu ShipMember'; else { echo 'Retour au menu Administration'; echo 'Revenir à la liste des bateaux'; echo 'Modifier'; } echo '
'; //------------------------------- // Help echo ''; echo '
'; echo '
'; echo '
'; break; } //************************************************************************************************************************ case "Creation_bateau": case "Modification_bateau": { echo '
'; echo '

Bateaux

'; echo '
'; echo Champ_jeton_csrf(); if ($_SESSION['Bateaux']['page'] == "Creation_bateau") echo '

Nouveau bateau

'; else echo '

Modification du bateau '.htmlspecialchars($_SESSION['Bateaux']['bateau']['Nom']).'

'; //---------------------------------------- // Nom : echo '
Nom
'; //---------------------------------------- // Date de mise en service : echo '
Date de mise en service
'; //---------------------------------------- // Flotte : echo '
Flotte à laquelle le bateau appartient
'; //---------------------------------------- // Commentaires : echo '
Commentaires
'; //---------------------------------------- // Boutons de bas de page : echo '
'; if ($_SESSION['Bateaux']['page'] == "Creation_bateau") // Création : { echo 'Annuler'; echo ''; } else // Modification : { echo 'Annuler'; echo ''; echo 'Supprimer le bateau'; } echo '
'; echo '
'; echo '
'; break; } //**************************************************************************************************************************** case "Confirmation_suppression_bateau": { echo '
'; echo '

Bateaux

'; echo '
'; echo '

Confirmez-vous la suppression du bateau '.htmlspecialchars($bateau_a_supprimer['Nom']).' ?

'; echo '

Si oui, son entrée dans la base de données sera dévalidée.

'; echo '
'; // Confirmation envoyée en POST avec le jeton de session (auparavant : un simple lien GET suffisait) : echo '
'; echo Champ_jeton_csrf(); echo 'Annuler'; echo ''; echo '
'; echo '
'; break; } } echo '
'; Pied_de_page(); ?>