0 ? 'Retour au TFE' : 'Retour à l\'accueil'; echo '
' . $backLink . '
Ce lien d\'accès est invalide ou incomplet.
', $thesisId); } // Generate (or reuse) CSRF token in session App::boot(); if (empty($_SESSION['csrf_token'])) { $_SESSION['csrf_token'] = bin2hex(random_bytes(32)); } // Minimal pre-check: does the token exist and look valid? // (Full redemption + one-time mark only happens on POST) $db = Database::getInstance(); $check = $db->getPDO()->prepare( "SELECT fat.expires_at, fr.thesis_id FROM file_access_tokens fat JOIN file_access_requests fr ON fat.request_id = fr.id WHERE fat.token = ? AND fat.is_valid = 1 AND fat.used_at IS NULL AND fat.expires_at > CURRENT_TIMESTAMP AND fr.status = 'approved' AND fr.thesis_id = ? LIMIT 1" ); $check->execute([$token, $thesisId]); $valid = $check->fetch(); if (!$valid) { renderError(403, 'Lien d\'accès invalide ou expiré', 'Ce lien a déjà été utilisé ou a expiré. Veuillez soumettre une nouvelle demande.
', $thesisId); } $csrfToken = $_SESSION['csrf_token']; $safeToken = htmlspecialchars($token, ENT_QUOTES); ?>Cliquez sur le bouton ci-dessous pour activer l'accès aux fichiers de ce TFE sur cet appareil.
L'accès sera valide pendant 30 jours sur cet appareil et navigateur.
Les données du formulaire sont invalides.
'); } $db = Database::getInstance(); // Redeem the one-time token (marks it used, logs audit trail) $ip = $_SERVER['REMOTE_ADDR'] ?? ''; $ua = substr($_SERVER['HTTP_USER_AGENT'] ?? '', 0, 512); $redemption = $db->redeemAccessToken($token, $ip, $ua); if (!$redemption || $redemption['thesis_id'] !== $thesisId) { renderError(403, 'Lien invalide ou déjà utilisé', 'Ce lien d\'accès est invalide, a déjà été utilisé, ou ne correspond pas au TFE demandé.
Si vous avez besoin d\'un nouvel accès, veuillez soumettre une nouvelle demande.
', $thesisId); } // Create a long-lived browser session (separate from the one-time email token) $sessionToken = $db->createAccessSession($redemption['request_id'], 30); // Set HttpOnly, Secure, SameSite=Strict cookie (long-lived session) $cookieName = 'tfe_access_' . $thesisId; $cookieSecure = !empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off'; setcookie($cookieName, $sessionToken, [ 'expires' => time() + 30 * 86400, 'path' => '/', 'domain' => '', 'secure' => $cookieSecure, 'httponly' => true, 'samesite' => 'Strict', ]); // Rotate CSRF token after successful action $_SESSION['csrf_token'] = bin2hex(random_bytes(32)); // Redirect to TFE page (no token in URL) header('Location: /tfe?id=' . $thesisId); exit; } // ── Any other method ────────────────────────────────────────────────────────── http_response_code(405); header('Allow: GET, POST'); echo 'Méthode non autorisée'; exit;