Formulaire de contact en php

Publié le : 19-01-2019 19:50

Introduction

L'objectif de cet article est d'expliqué comment créer un formulaire de contact simple et sécurisé.

Le formulaire HTML

Le noeud form contient l'attribut method qui définit si il faut envoyer la demande en GET (visible dans l'url finale) ou en POST (invisible dans l'url finale). Et l'attribut action qui cible le script PHP à appeler.

Le premier noeud input de type email attendra une donnée de type email toute autre format sera refusé.

Le second noeud input de type text attendra n'importe quelle donnée.

<form method="post" action="contact.php">
   <input type="email" name="email" placeholder="nom.prenom@exemple.fr" />
   <input type="text" name="content" placeholder="Votre message" />
   <button type="submit">Envoyer</button>
</form>

La sécurité et le HTML

En cas de modification du code HTML il est possible de remplacer le type d'un input par un autre, ainsi un utilisateur mal intentionné pourrait à sa guise transformer un champ email en champ texte et envoyer les données qu'il souhaite.

De même les données transmises en POST bien qu'invisible dans l'URL du navigateur sont visibles en cas d'analyse via la console (raccourcie F12 > onglets console > Requêtes)

Il est donc fondamental de bien comprendre que tout ce qui émane du client est à considérer comme fallacieux et doit par la suite être contrôlé dans le code côté serveur.

Le code PHP du fichier contact.php

//Initialisation de l'objet PDO et ouverture de la connexion pour appel à la base de données
$Pdo_Object = new PDO("mysql:host=127.0.0.1;dbname=DataBase","user","password",array(PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION )); 

try {
   //Contrôle de l'éxistance des deux paramètres email et content
   if(!isset($_POST['email'])) throw new Exception("Le paramètre email est absent");
   if(!isset($_POST['content'])) throw new Exception("Le paramètre content est absent");
   
   //Contrôle des formats des deux paramètres via les expressions régulières
   $Format_Email = '#[a-z0-9]{1,}[\-\_\.a-z0-9]{0,}@[a-z]{2,}[\-\_\.a-z0-9]{0,}\.[a-z]{2,6}$#';
   $Format_Content = '#^[a-zA-Z0-9áàâäãåçéèêëíìîïñóòôöõúùûüýÿæœÁÀÂÄÃÅÇÉÈÊËÍÌÎÏÑÓÒÔÖÕÚÙÛÜÝŸÆŒ\.\_\-\s]{5,500}$#'
   if(!preg_match($Format_Email, $_POST['email']))  throw new Exception("Le paramètre email ne correspond pas au format attendu");
   if(!preg_match($Format_Content , $_POST['content']))  throw new Exception("Le paramètre content ne correspond pas au format attendu - limite de 500 caractères");
 
  //Tableau associatif pour requête d'insertion 
  $Arr_Key_Value = array(
                         'email' => $_POST['email'],
                         'content' => $_POST['content']);
  //Requête d'insertion
  $Sql_Query = "INSERT INTO contact(email,content) VALUES (:email,:content)";
  
  //Préparation de la requête (sécurisation des variables du tableau associatif)
  $Request= $Pdo_Object->prepare($Sql_Query);
  
  //Exécution de la requête 
  $Request->execute($Arr_Key_Value);
} catch (Exception $e) {
   echo $e->getMessage(); 
}
finally{
 //Attention le finaly ne fonctionne que sur php 5.6 et supérieur 
 //Fermeture de la connexion en détruisant la référence mémoire à l'objet PDO
 $Pdo_Object = null;
}