Séquence 7 · 5-6h

PHP & MySQL — Les données

Connexion PDO, requêtes SQL, formulaire → BDD → affichage, sécurité de base.

Objectif : Créer un formulaire de contact fonctionnel qui sauvegarde en base de données.

C
Cours

Connexion à la base de données avec PDO

PDO (PHP Data Objects) est la méthode moderne et sécurisée pour se connecter à MySQL en PHP.

<?php
// config/db.php
define("DB_HOST", "localhost");
define("DB_NAME", "ma_base");
define("DB_USER", "root");
define("DB_PASS", "");

function getDB() {
    static $pdo = null;
    if ($pdo === null) {
        try {
            $dsn = "mysql:host=" . DB_HOST . ";dbname=" . DB_NAME . ";charset=utf8mb4";
            $pdo = new PDO($dsn, DB_USER, DB_PASS, [
                PDO::ATTR_ERRMODE            => PDO::ERRMODE_EXCEPTION,
                PDO::ATTR_DEFAULT_FETCH_MODE => PDO::FETCH_ASSOC,
            ]);
        } catch (PDOException $e) {
            die("Connexion impossible : " . $e->getMessage());
        }
    }
    return $pdo;
}
?>
C
Cours

Requêtes SELECT — lire des données

<?php
$db = getDB();

// Récupérer tous les projets
$stmt = $db->query("SELECT * FROM projets ORDER BY created_at DESC");
$projets = $stmt->fetchAll();

// Récupérer un projet par ID (requête préparée)
$id = 3;
$stmt = $db->prepare("SELECT * FROM projets WHERE id = :id");
$stmt->execute([":id" => $id]);
$projet = $stmt->fetch();
?>

<!-- Afficher dans le HTML -->
<?php foreach ($projets as $p) : ?>
  <div class="carte">
    <h3><?= htmlspecialchars($p["titre"]) ?></h3>
    <p><?= htmlspecialchars($p["description"]) ?></p>
  </div>
<?php endforeach; ?>

Les requêtes préparées (avec :parametre) protègent contre les injections SQL. Toujours les utiliser avec des données utilisateur.

C
Cours

Requêtes INSERT — sauvegarder des données

<?php
if ($_SERVER["REQUEST_METHOD"] === "POST") {
    $nom     = trim($_POST["nom"] ?? "");
    $email   = trim($_POST["email"] ?? "");
    $message = trim($_POST["message"] ?? "");

    $erreurs = [];
    if ($nom === "")                     $erreurs[] = "Nom obligatoire.";
    if (!filter_var($email, FILTER_VALIDATE_EMAIL)) $erreurs[] = "Email invalide.";
    if (strlen($message) < 10)           $erreurs[] = "Message trop court.";

    if (empty($erreurs)) {
        $db = getDB();
        $stmt = $db->prepare(
            "INSERT INTO contacts (nom, email, message, created_at)
             VALUES (:nom, :email, :message, NOW())"
        );
        $stmt->execute([
            ":nom"     => $nom,
            ":email"   => $email,
            ":message" => $message,
        ]);
        $succes = "Message envoyé, merci !";
    }
}
?>
T
Astuce

Sécurité de base — les règles d'or

  • Ne jamais faire confiance aux données utilisateur. Valide et nettoie toujours côté serveur.
  • Requêtes préparées obligatoires dès qu'une variable utilisateur entre dans une requête SQL.
  • htmlspecialchars() pour tout ce qu'on affiche dans le HTML.
  • Ne jamais afficher les erreurs en production. En dev : error_reporting(E_ALL);. En prod : logs seulement.
  • Mots de passe : jamais en clair. Utiliser password_hash() et password_verify().
  • HTTPS : toujours en production. Sur Plesk, c'est gratuit avec Let's Encrypt.
P
Projet

Projet — Formulaire de contact avec BDD

Ce que tu vas construire

Un formulaire de contact complet : l'utilisateur remplit le formulaire, les données sont sauvegardées en base, et tu peux les voir dans une page d'administration.

Tables à créer

CREATE TABLE contacts (
  id INT AUTO_INCREMENT PRIMARY KEY,
  nom VARCHAR(100) NOT NULL,
  email VARCHAR(200) NOT NULL,
  message TEXT NOT NULL,
  lu TINYINT(1) DEFAULT 0,
  created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);

Pages à créer

  • contact.php — formulaire avec validation PHP
  • admin-messages.php — liste des messages reçus (protégée par mot de passe)

Ce qu'on évalue

  • Requêtes préparées utilisées
  • Validation serveur complète
  • htmlspecialchars() partout
  • Affichage propre des messages côté admin

Tu as terminé les leçons de cette séquence ?

Quiz — Séquence 7

Vérifie ta compréhension avant de passer à la suite. Réponds à toutes les questions, puis valide.

Question 1/3
Pourquoi utiliser des requêtes préparées en PDO ?
Question 2/3
Quelle méthode PDO exécute une requête et retourne tous les résultats ?
Question 3/3
Comment sécuriser un mot de passe en PHP ?