[php] envoi de formulaires par mail

Fermé
Signaler
Messages postés
9
Date d'inscription
samedi 20 janvier 2007
Statut
Membre
Dernière intervention
18 octobre 2007
-
Messages postés
1
Date d'inscription
vendredi 12 février 2010
Statut
Membre
Dernière intervention
12 février 2010
-
Bonjour,

J'ai créé un formulaire qui ajoute des données dans une BD MySQL. Je reçois également un mail avec les résultats de mon formulaire.

Ce que je voudrais, c'est que la personne qui rempli mon formulaire et qui entre son adresse e-mail dans le champ prévu à cet effet, reçoive le même mail de confirmation que moi...

le champ e-mail n'est pas obligatoire dans mon formulaire.

Voici le code que j'utilise pour me faire parvenir le mail:


<?php
$TO = "mon_nom@mon_domaine.ch";

$h = "From: " . $TO;

$message = "";

while (list($key, $val) = each($HTTP_POST_VARS)) {
$message .= "$key : $val\n";
}

mail($TO, $subject, $message, $h);

Header("Location: http://page de confirmation.html");

?>

Quelqu'un aurait une solution mettre sous la dent d'un débutant...?

Merci d'avance...

21 réponses

Messages postés
2884
Date d'inscription
samedi 29 juillet 2006
Statut
Modérateur
Dernière intervention
15 août 2020
824
Salut.

Tu as de gros problèmes de sécurité dans ton code.
Je te recommande de supprimer tout de suite la requête dans ton code, et de mettre à jour le fichier sur le site.
Enlève le "mysql_query(...)", tu peux laisser le reste.

Je vais éditer ce message, mais je poste vite pour que tu le voies.


Bon, l'édition maintenant.

Je te donne un code, et la liste des fonctions que j'utilise.
Si tu copies/colles ce code il fonctionnera (tu dois quand même mettre les informations de ta base de données et ton adresse e-mail), mais ca ne servira à rien.

Je te conseille de te rendre sur la documentation PHP pour voir à quoi servent les fonctions et pourquoi je les utilise.

Les fonctions


(dans l'ordre d'utilisation)
Ces explication sont sommaires et pas forcément exactes.
Consulte la documentation ;-)
get_magic_quotes_gpc : pemet de voir si des anti-slashs sont ajoutés automatiquement sur certaines variables qui proviennent de l'utlisateur, comme les $_POST.
array_map : Permet d'appliquer une fonction à tous les éléments d'un array à la fois.
stripslashes : Enlève les anti-slashs qui servent d'échappement dans une variable.
mysql_real_escape_string : Echappe les caractères selon les normes MySQL.
htmlspecialchars : Remplace certains caractères html (comme < et >) par leus entités.
extract : Extrait tout les éléments d'un array.
Par exemple :
$truc['champ']='str';
extract($truc);
//maintenant $champ vaut 'str'


Et quelques autres trucs que j'utilise mais qui ne sont pas des fonctions :
foreach : Boucle qui permet de parcourir un array clé par clé et valeur par valeur, et d'appliquer les mêmes choses à chaque fois.

Le code


<?
//on rend innofensives les données (seulement le html ici)
  if(get_magic_quotes_gpc())
    $_POST=array_map('stripslashes',$_POST);
  $_POST=array_map('trim',$_POST);
  foreach($_POST as $champ=>$valeur)
    $_POST[$champ]=htmlspecialchars($valeur,ENT_NOQUOTES);
  $date=date('d/m/Y H:i:s');

//connection a MySQL et selection de la BDD
  $ConnectionBDD=mysql_connect('localhost','NomUtilisateur','MotDePasse','')or die('Erreur de connexion '.mysql_error());
  mysql_select_db('ma_db',$ConnectionBDD) or die('Erreur de selection'.mysql_error());

//insertion des données dans la BDD, APRES SECURISATION POUR SQL !!
  $postSQL=$_POST;
  foreach($postSQL as $champ=>$valeur)
    $postSQL[$champ]=mysql_real_escape_string($valeur);
  extract($postSQL);
  $RQSQLinsertionDonnees="INSERT INTO ma_table VALUES('$nom','$prenom','$jour','$mois','$annee','$sexe','$rue','$npa','$lieu','$tel','$categorie','$email','$remarques','$sujet','$date')";
  mysql_query($RQSQLinsertionDonnees) or die('Erreur SQL !'.$RQSQLinsertionDonnees.'<br>'.mysql_error());

mysql_close();


//on prépare les données pour envoyer le mail
  $header='From: '.$destinataire."\r\n".'Content-type:text/plain;charset=iso-8859-1';
  $message='';

//tous les champs du formulaire sont ajoutés dans le message
  foreach($_POST as $cle=>$valeur)
    $message.=$cle.' : '.$valeur."\n";

//on envoie le mail en séparant les adresse des deux destinataires par une virgule et un espace dans le premier argument de la fonction
  mail('tonadresse@email.tld, '.$email,$subject,$message,$header);

//on dirige vers le résultat, mais on eput le faire au début, seulement on ne verra pas les erreurs s'il y en a.
  header('Location: http://ma_page_de_confirmation.html');
?>



j'éspère que je t'ai aidé, et que tu ne vas pas copier/coller le code bêtement sans comprendre ;-)

a plus
9
Messages postés
2884
Date d'inscription
samedi 29 juillet 2006
Statut
Modérateur
Dernière intervention
15 août 2020
824
Salut.

Ton code est un peu bizarre, et pas du tout optimisé.
La variable"$subject", d'ou vient-elle ?

Si j'ai bien compris, tu veux envoyer le même mail à toi et la personne qui te l'envoie.
Tu as deux solutions : utiliser une syntaxe qui permet d'envoyer le mail à plusieurs personnes ou utiliser deux fois la fonction mail.
Essaye : (en n'oubliant pas de mettre la deuxième adresse)
<?php
//on définir et initialise quelques variables
$destinataire='mon_nom@mon_domaine.ch';
$header='From: '.$destinataire;
$message='';

//tous les champs du formulaire sont ajoutés dans le message
foreach($_POST as $cle=>$valeur)
  $message.=$cle.' : '.$valeur."\n";

//on envoie le mail en séparant les adresse des deux destinataires par une virgule et un espace
mail($destinataire.', deuxiemeadresse',$subject,$message,$header);

//on dirige vers le résultat
header('Location: http://page de confirmation.html');
?>
5
Messages postés
9
Date d'inscription
samedi 20 janvier 2007
Statut
Membre
Dernière intervention
18 octobre 2007
6
Hello Ssylvainsab,

Pour répondre à ta question, j'ai récuperé ce bout de code d'un exemple que j'ai touvé sur le net et je l'ai adapté à mon formulaire. Mais comme je disais je suis un vrai novice, donc je ne sais pas encore distinguer qu'est ce qui est utile de ce qui ne l'est pas mais ça fonctionnait....

Merci pour ta réponse, je vai tester ta solution...
0
Messages postés
2884
Date d'inscription
samedi 29 juillet 2006
Statut
Modérateur
Dernière intervention
15 août 2020
824
Si ca ne marche pas, donne le code complet de ton script en utilisant le bouton code.
2
Messages postés
9
Date d'inscription
samedi 20 janvier 2007
Statut
Membre
Dernière intervention
18 octobre 2007
6
Bon bein j'ai essayé mais ça le fait pas...

Je reçois le mail de confirmation à l'adresse que j'ai indiqué sous $destinataire, mais pas le mail qui doit être envoyé à la personne qui rempli le formulaire

Alors voilà le code complet avec ta version pour l'envoi du mail:


<?
//partie du code qui insère les valeurs de mes champs de formulaire dans ma base de données (qui fontionne parfaitement)

$nom = $_POST['nom'];
$prenom = $_POST['prenom'];
$jour = $_POST['jour'];
$mois = $_POST['mois'];
$annee = $_POST['annee'];
$sexe = $_POST['sexe'];
$rue = $_POST['rue'];
$npa = $_POST['npa'];
$lieu = $_POST['lieu'];
$tel = $_POST['tel'];
$categorie = $_POST['categorie'];
$email = $_POST['email'];
$remarques = $_POST['remarques'];
$sujet = $_POST['sujet'];
$date = date("d/m/Y H:i:s");


$db = mysql_connect('localhost', 'NomUtilisateur', "MotDePasse", '') or die('Erreur de connexion '.mysql_error());


mysql_select_db('ma_db',$db) or die('Erreur de selection'.mysql_error());


$sql = "INSERT INTO ma_table VALUES('$nom','$prenom','$jour','$mois','$annee','$sexe','$rue','$npa','$lieu','$tel','$categorie','$email','$remarques','$sujet','$date')";


mysql_query($sql) or die('Erreur SQL !'.$sql.'<br>'.mysql_error());



mysql_close();

//Le code que tu m'as donné

//on défini et initialise quelques variables
$destinataire='mon_nom@mon_domaine.ch';
$header='From: '.$destinataire;
$message='';

//tous les champs du formulaire sont ajoutés dans le message
foreach($_POST as $cle=>$valeur)
$message.=$cle.' : '.$valeur."\n";

//on envoie le mail en séparant les adresse des deux destinataires par une virgule et un espace
mail($destinataire, ??????, $subject,$message,$header);

//on dirige vers le résultat
header('Location: http://ma_page_de_confirmation.html');
?>

J'ai mis des ?????? à l'endroit ou je souhaite récuperer l'adresse mail qui sera saisie dans le champ "$email" de mon formulaire (qui sera donc l'adresse de messagerie des personnes qui rempliront le formulaire)

J'espère que je suis pas trop compliqué à suive... :O)

Sinon, voici l'adresse de mon formulaire d'inscription:

http://www.zinalfreeride.ch/Forms/Inscriptions_.html

Encore merci pour les réponses...

Sam
2
Messages postés
9
Date d'inscription
samedi 20 janvier 2007
Statut
Membre
Dernière intervention
18 octobre 2007
6
Salut Sylvain,

Je te remercie pour ta réponse et pour la mise en garde au sujet du problème de sécurité...!!!

J'ai enlevé le bout de code dont tu m'as parlé lié au problème de sécurité mais du coup les données ne s'inscrivaient plus dans la base de donnée.

Alors pour être franc, j'ai fait ce que tu m'as déconseillé, j'ai copié/collé bêtement le code en faisant les modifications nécessaires et ça fonctionne à merveille.... Mais soit rassuré, je ne compte pas rester ignorant toute ma vie et je vais potasser pour comprendre le sens du code car j'ai d'autres projets dans un futur plus ou moins proche...


Je n'avais pas la possibilité de laisser le formulaire indisponible, on organise une compétition de freeride le 1er week-end de mars et si personne ne peut s'inscrire on aurait un gros souci...

Bref, je vais pas te raconter toute ma vie (t'as sûrement d'autres choses plus intéressantes à faire :-) mais je tiens à te remercier pour le temps que tu as consacré à mon problème et pour tes conseils éclairés...

Si j'ose me permettre, quel était le risque avec mon ancien code: qu'on puisse y accéder et modifier des paramètre ou tout simplement qu'on puisse détruire la base ou encore plus grave...!?!?

Voilà, ni une ni deux, je retourne à l’école du PHP, potasser le code que tu m’as envoyé…
Encore mille mercis...

Sam


PS: désolé pour le bouton CODE, j'y penserai la prochaine fois, promis... :-<
1
Messages postés
2884
Date d'inscription
samedi 29 juillet 2006
Statut
Modérateur
Dernière intervention
15 août 2020
824
Salut.

J'ai enlevé le bout de code dont tu m'as parlé lié au problème de sécurité mais du coup les données ne s'inscrivaient plus dans la base de donnée.
C'est normal. Mais il valait mieux ca qu'une injection SQL.
Maintenant que le problème est réglé, c'est bon.


Alors pour être franc, j'ai fait ce que tu m'as déconseillé, j'ai copié/collé bêtement le code en faisant les modifications nécessaires et ça fonctionne à merveille.... Mais soit rassuré, je ne compte pas rester ignorant toute ma vie et je vais potasser pour comprendre le sens du code car j'ai d'autres projets dans un futur plus ou moins proche...
C'est pas grave, si c'est parce que ton formulaire est urgent, tu pourras apprendre plus tard.
Surtout grâce aux liens que je t'ai donné.
L'important c'est que tu puisses comprendre le code, et comme ca tu pourras le modifier si tu veux.


Si j'ose me permettre, quel était le risque avec mon ancien code: qu'on puisse y accéder et modifier des paramètre ou tout simplement qu'on puisse détruire la base ou encore plus grave...!?!?
On pouvait au pire détruire ta base et tes tables, et si l'on est malin, afficher les données avant.
Voir le lien sur les injections sql donné plus haut.
Par exemple, si on entre un apostrophe, on peut mettre ce que l'on veut après, et ce sera pris en compte comme du code SQL (et peut-être PHP mais je ne suis pas sur).


Une autre question, dans ton code, tu fais ca :
$date = date("d/m/Y H:i:s");
Et ensuite tu l'insères dans ta base de données.
Quel est le type du champ correspondant ?


a plus
1
Messages postés
9
Date d'inscription
samedi 20 janvier 2007
Statut
Membre
Dernière intervention
18 octobre 2007
6
Salut,

Tes précisions me sont précieuses, ça aide à mieux comprendre mais j'ai encore du boulôt pour tout assimiler ...

En ce qui concerne le champ "date" dans ma base de données, il est au format "DATETIME".
J'utilise ce champ plus comme info qu'autre chose mais ça me permet aussi de savoir quel enregistrement est le plus récent quand une personne se réinscrit une deuxième fois pour corriger des données ou des erreurs de saisie dans le formulaire... Ca me permet aussi de faire des esportations de données en utilisant ce champ comme filtre.

Voici comment la date apparaît dans ma DB:

20/01/2007 17:33:36

Je suppose que si tu me poses la question, c'est pas par hasard...?

Même si je l'ai dit jéjà un paquet de fois, merci encore...

Sam
1
Messages postés
2884
Date d'inscription
samedi 29 juillet 2006
Statut
Modérateur
Dernière intervention
15 août 2020
824
Salut.

j'ai encore du boulôt pour tout assimiler ...
A force de pratique, ca viendra ;-)
Ah, retiens cette phrase :
"Never trust user input", qui veut dire : "Ne jamais faire confiance à une entrée de l'utilisateur".


En ce qui concerne le champ "date" dans ma base de données, il est au format "DATETIME".
Je suppose que si tu me poses la question, c'est pas par hasard...?

Oui.
C'est parce que certaines personnes recommandent de stocker les dates dans des champs qui n'ont rien à voir, comme Varchar, int, ou même float !!
C'est n'importe quoi.
Il y a des formats date, time et datetime dans MySQL, et c'est pas pour rien.
Tu utilises le bon type de champ ;-)
Voir ces deux liens :
http://expreg.com/expreg_article.php?art=timestamp
http://expreg.com/expreg_article.php?art=timestamp_bis


a plus
1
Bonjour,

Sylvain, juste une question :
n'y a t-il pas une faille de sécurité en utilisant la fonction extract() ??

Je suis simple débutant en php...

Merci

Flo
1
Messages postés
2884
Date d'inscription
samedi 29 juillet 2006
Statut
Modérateur
Dernière intervention
15 août 2020
824
Effectivement !!
Il y a une faille de sécurité avec extract !
Merci Florent !
Il ne vaut mieux pas l'utiliser et faire comme tu faisais avant LESAM, avec $champ=$_POST['champ'] ;-)

Donc, à la place de "extract($postSQL);", il faut mettre :
  $nom=       $postSQL['nom'];
  $prenom=    $postSQL['prenom'];
  $jour=      $postSQL['jour'];
  $mois=      $postSQL['mois'];
  $annee=     $postSQL['annee'];
  $sexe=      $postSQL['sexe'];
  $rue=       $postSQL['rue'];
  $npa=       $postSQL['npa'];
  $lieu=      $postSQL['lieu'];
  $tel=       $postSQL['tel'];
  $categories=$postSQL['categories'];
  $email=     $postSQL['email'];
  $sujet=     $postSQL['sujet'];
  $date=      $postSQL['date'];
1
Messages postés
9
Date d'inscription
samedi 20 janvier 2007
Statut
Membre
Dernière intervention
18 octobre 2007
6
Hello,

Merci pour l'info, je vais faire la correction.

Bonne journée...

Sam

PS: quel est le problème avec "extract"...? A titre de formation personnelle...
1
Messages postés
9
Date d'inscription
samedi 20 janvier 2007
Statut
Membre
Dernière intervention
18 octobre 2007
6
Hello Flo,

Merci pour tes précisions...

Bon week end.

Sam
1
Messages postés
2884
Date d'inscription
samedi 29 juillet 2006
Statut
Modérateur
Dernière intervention
15 août 2020
824
Si je ne me trompe pas, la fonction extract() revient à mettre register_global sur on pour le tableau ciblé.
Exact ;-)
1
Bonjour,

Mon association réuni des personnes qui peuvent donner des conseils.

Je souhaite mettre un formulaire sécurisé pour éviter d'être spamé par des robot et illuminer les faux mail.

Pour cela, je souhaite que les personnes qui pause une question soit obliger de cliquer sur un lien envoyé par mail pour valider leur question.

Est-ce possible?

Julie
1
Bonjour,

je trouve ce système un peu lourd pour celui qui pose la question, pourquoi ne prends tu pas un système de code ou de lettre que la personne doit recopier pour valider le message, un peu comme le système mis en place sur ce site...
1
Bonjour,

Tout d'abord merci pour toutes ces informations, dommage que Google ne référence pas mieux ce genre de pages bien plus utiles que d'autres qui sont devant :(

Je n'ai pas tout a fait compris en quoi l'utilisation de extract() serait une faille de sécurité ?

Est-ce à cause d'une éventuelle modification du code html de la page avant l'envoi du formulaire ?

Merci d'avance ;)
1
Messages postés
2884
Date d'inscription
samedi 29 juillet 2006
Statut
Modérateur
Dernière intervention
15 août 2020
824
Salut.

"Je n'ai pas tout a fait compris en quoi l'utilisation de extract() serait une faille de sécurité ?
Est-ce à cause d'une éventuelle modification du code html de la page avant l'envoi du formulaire ?"

Oui, par exemple.
Il suffit que quelqu'un ajoute une variable POST et lui donne un certain nom.
Si tu utilises une variable du même nom dans le traitement de tes données, ça peut être dangereux d'utiliser la fonction extract.
Par exemple, si utilises une variable nommée $truc, et que quelqu'un a ajouté une variable POST avec pour nom truc, en utilisant extract, $truc vaudra ce que ce quelqu'un a défini (et pas la valeur que tu lui a donné).
Ensuite, il peut faire plus ou moins de dégâts selon ce que tu fais de la variable.
--
Sylvain
0
Ok je vois, merci beaucoup pour ta réponse. Finalement le risque n'est pas bien grand, il faut vraiement insister pour trouver de telles failles ^^.

Au moins je suis prévenu.
1
Salut,
J'ai un problème pour la ligne du message de confirmation,
header("location: contact-ok.html");

Elle a marché une fois, et j'ai une erreur maintenant :
Warning: Cannot modify header information - headers already sent by (output started at /-chemin-vers-la-page-/mail.php:1) in /-chemin-vers-la-page-/mail.php on line 8

Quelqu'un a t'il un autre moyen pour afficher une page de confirmation, ou peut voir ce qui ne va pas ? D'autant plus que je reçoit bel et bien le mail ! Voilà le fichier PHP complet :
<?php
$de= "adresse@mail";
$entete= "Reply-To: $Mail";
$entete = "From: $Nom <$Mail>";
$sujet= "Contact";
$contenu= "De : $Nom \nAdresse : $Mail \nMessage : $Message";
mail($de, $sujet, $contenu, $entete);
header("location: contact-ok.html");
?>
1
Messages postés
1
Date d'inscription
vendredi 12 février 2010
Statut
Membre
Dernière intervention
12 février 2010

hello a vous tous,

Bien voilou,
je retourne un peu tous les sites pour pouvoir comprendre comment je dois procéder pour que mon formulaire soit envoyé par mail a l'adresse mail que je voudrais et j'avoues que je galère assez....
je débute dans le domaine, réussi a créé mon formulaire il y a quelques jours ainsi que la page de remerciements en html.
Après avoir fait ceux ci je n'arrive pas a savoir si je dois vraiment bosser en php pour pouvoir ajouter cette adresse....
pour le php notepad est-il aussi bien aussi?

Merci a vous d'avance
0
Bonjour,

"int extract ( array var_array , int extract_type , string prefix )

extract sert à exporter un tableau vers la table des symboles. Elle prend un tableau associatif var_array , crée les variables dont les noms sont les index de ce tableau, et leur affecte la valeur associée. Pour chaque paire clé/valeur, extract crée une variable, avec les paramètres extract_type et prefix . "

Si je ne me trompe pas, la fonction extract() revient à mettre register_global sur on pour le tableau ciblé.

Flo
0
Messages postés
55
Date d'inscription
jeudi 3 avril 2008
Statut
Membre
Dernière intervention
19 juin 2008
43
Bonjour,

moi j'ai aussi un gros problème avec outlook quand j'envoie un message mon recepte resois 10 méssage, souven cela arrive quand je joint une pièce a ce message

Quelqu'un connais t'il la solution a mon problème?

merci cdt
0