Bienvenue sur Induste !

En vous inscrivant, vous pourrez discuter, partager et envoyer des messages privés avec d'autres membres de notre communauté.

Je m'inscris !

Sécurisez vos formulaires - PHP

Walky 🇫🇷

Cryptoboy
Ancien staff
Inscription
18 Octobre 2012
Messages
1 268
Réactions
1 187
Points
17 650
    Réponse de Walky 🇫🇷 Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #1
header1.png

Bonjour à tous , aujourd'hui nous allons, ensemble, apprendre à sécuriser nos formulaires HTML.

header2.png
Bien évidemment, nous n'utiliserons pas de vérification Captcha ou ReCaptcha pour ne pas embêter le visiteur.

Le principe va consister à générer une clé secrète pour l'insérer dans un champ invisible dans notre formulaire.
Et lors de l'envoi du formulaire, nous allons vérifier la validité de la clé.

Pour générer notre clé secrètre, nous utiliserons deux paramètres:

  • Un salt (de préférence tapé à la main)
  • Le timestamp actuel
Veillez à ne pas utiliser de variables statiques, voilà pourquoi j'utilise le timestamp .

header3.png
Comme vu dans la partie précédente, nous utiliserons deux paramètres, mais vous vous doutez bien qu'on ne les affichera pas directement dans le formulaire (même en champ masqué), on va donc utiliser une fonction PHP permettant de crypter les données , dans ce tutoriel je vais utiliser SHA1.

Commençons donc par créer notre seul et unique fichier, qui contiendra le formulaire HTML ainsi que le code PHP .


Je tiens à vous informer que j'utiliserai la POO tout au long du tutoriel.
PHP:
<?php

class SubmitForm
{
    public $salt   = '782hdbbab001mbdjbxaoi9'; // tapé à la main
    public $erreur = null; // ici, sera stocké l'erreur

    public function __construct()
    {
        session_start(); // on démarre la session
        $_SESSION['key'] = uniqid(microtime(true)); // on stocke notre clé relative au timestamp dans une variable de session
    }

    public function buildKey()
    {
        if (!isset($_SESSION['key'])) // la variable de session "key" doit obligatoirement exister
        {
            $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        $secretKey = sha1($_SESSION['key'] . $this->salt);
        return $secretKey;
    }
}

On constate donc qu'il y a une variable de class: $salt, contenant notre salt, ainsi que 2 fonctions. L'une, exécutée directement lors du chargement de la page, et une autre permettant de générer la clé secrète .

À cela on va ajouter le formulaire HTML , de base un formulaire non sécurisé ressemble à ceci:
HTML:
<!DOCTYPE html>
<html>
    <head>
        <!-- Vos données -->
    </head>
    <body>
        <form method="post" action="/">
            <input type="text" name="prenom" placeholder="Prénom..." />
            <input type="text" name="age" placeholder="Age..." />

            <input type="submit" value="Soumettre" />
        </form>
    </body>
</html>

On va donc stocker notre clé secrète dans une variable, générée par notre fonction créée précédemment.

PHP:
$class     = new SubmitForm();
$secretKey = $class->buildKey();

Et l'insérer dans un champ invisible dans le formulaire HTML
PHP:
<input type="hidden" name="key" value="<?= $secretKey ?>" />

Il ne nous reste donc, seulement la vérification de la clé ! Et afficher l'erreur dans le formulaire HTML
PHP:
public function verifyKey()
{
    if (!isset($_SESSION['key'])) // la variable de session "key" doit obligatoirement exister
    {
        $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
        return false;
    }

    if (!isset($_POST['key'])) // le formulaire doit contenir le champ "key"
    {
        $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
        return false;
    }

    $secretKey = sha1($_SESSION['key'] . $this->salt);
    if ($_POST['key'] != $secretKey) // la clé secrète envoyée doit correspondre exactement à celle créée par la fonction
    {
        $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
        return false;
    }

    return true;
}

En dehors de la class, nous avons donc quelque chose du genre
PHP:
$class     = new SubmitForm();
$secretKey = $class->buildKey();

if ($_SERVER['REQUEST_METHOD'] == 'post') // on vérifie la clé seulement si la requête envoyée est au format POST
{
    $class->verifyKey();
}

header4.png
PHP:
<?php

class SubmitForm
{
    public $salt   = '782hdbbab001mbdjbxaoi9';
    public $erreur = null;

    public function __construct()
    {
        session_start(); // on démarre la session
        $_SESSION['key'] = uniqid(microtime(true)); // on stocke notre clé relative au timestamp dans une variable de session
    }

    public function buildKey()
    {
        if (!isset($_SESSION['key']))
        {
            $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        $secretKey = sha1($_SESSION['key'] . $this->salt);
        return $secretKey;
    }

    public function verifyKey()
    {
        if (!isset($_SESSION['key'])) // la variable de session "key" doit obligatoirement exister
        {
            $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        if (!isset($_POST['key'])) // le formulaire doit contenir le champ "key"
        {
            $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        $secretKey = sha1($_SESSION['key'] . $this->salt);
        if ($_POST['key'] != $secretKey) // la clé secrète envoyée doit correspondre exactement à celle créée par la fonction
        {
            $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        return true;
    }
}

$class     = new SubmitForm();
$secretKey = $class->buildKey();

if ($_SERVER['REQUEST_METHOD'] == 'post') // on vérifie la clé seulement si la requête envoyée est au format POST
{
    $class->verifyKey();
}
?>

<!DOCTYPE html>
<html>
    <head>
        <!-- Vos données -->
    </head>
    <body>
        <?php
            if ($class->erreur)
            {
                echo $class->erreur;
            }
        ?>
        <form method="post" action="/">
            <input type="text" name="prenom" placeholder="Prénom..." />
            <input type="text" name="age" placeholder="Age..." />

            <input type="hidden" name="key" value="<?= $secretKey ?>" />
            <input type="submit" value="Soumettre" />
        </form>
    </body>
</html>

header5.png
Je vous remercie d'avoir lu ce tutoriel, et n'hésitez pas à me faire part de vos erreurs / bugs rencontrés si vous utilisez le système que je viens de vous présenter ::cool::

Merci @Lawid SEC pour les headers :love:

Walky
 

Fichiers joints

  • header1.png
    header1.png
    76.1 KB · Affichages: 145
D

deleted292225

    Réponse de deleted292225 Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #2
Voir la pièce jointe 101360
Bonjour à tous , aujourd'hui nous allons, ensemble, apprendre à sécuriser nos formulaires HTML.

Voir la pièce jointe 101356
Bien évidemment, nous n'utiliserons pas de vérification Captcha ou ReCaptcha pour ne pas embêter le visiteur.

Le principe va consister à générer une clé secrète pour l'insérer dans un champ invisible dans notre formulaire.
Et lors de l'envoi du formulaire, nous allons vérifier la validité de la clé.

Pour générer notre clé secrètre, nous utiliserons deux paramètres:

  • Un salt (de préférence tapé à la main)
  • Le timestamp actuel
Veillez à ne pas utiliser de variables statiques, voilà pourquoi j'utilise le timestamp .

Comme vu dans la partie précédente, nous utiliserons deux paramètres, mais vous vous doutez bien qu'on ne les affichera pas directement dans le formulaire (même en champ masqué), on va donc utiliser une fonction PHP permettant de crypter les données , dans ce tutoriel je vais utiliser SHA1.

Commençons donc par créer notre seul et unique fichier, qui contiendra le formulaire HTML ainsi que le code PHP .


Je tiens à vous informer que j'utiliserai la POO tout au long du tutoriel.
PHP:
<?php

class SubmitForm
{
    public $salt   = '782hdbbab001mbdjbxaoi9'; // tapé à la main
    public $erreur = null; // ici, sera stocké l'erreur

    public function __construct()
    {
        session_start(); // on démarre la session
        $_SESSION['key'] = uniqid(microtime(true)); // on stocke notre clé relative au timestamp dans une variable de session
    }

    public function buildKey()
    {
        if (!isset($_SESSION['key'])) // la variable de session "key" doit obligatoirement exister
        {
            $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        $secretKey = sha1($_SESSION['key'] . $this->salt);
        return $secretKey;
    }
}

On constate donc qu'il y a une variable de class: $salt, contenant notre salt, ainsi que 2 fonctions. L'une, exécutée directement lors du chargement de la page, et une autre permettant de générer la clé secrète .

À cela on va ajouter le formulaire HTML , de base un formulaire non sécurisé ressemble à ceci:
HTML:
<!DOCTYPE html>
<html>
    <head>
        <!-- Vos données -->
    </head>
    <body>
        <form method="post" action="/">
            <input type="text" name="prenom" placeholder="Prénom..." />
            <input type="text" name="age" placeholder="Age..." />

            <input type="submit" value="Soumettre" />
        </form>
    </body>
</html>

On va donc stocker notre clé secrète dans une variable, générée par notre fonction créée précédemment.

PHP:
$class     = new SubmitForm();
$secretKey = $class->buildKey();

Et l'insérer dans un champ invisible dans le formulaire HTML
PHP:
<input type="hidden" name="key" value="<?= $secretKey ?>" />

Il ne nous reste donc, seulement la vérification de la clé ! Et afficher l'erreur dans le formulaire HTML
PHP:
public function verifyKey()
{
    if (!isset($_SESSION['key'])) // la variable de session "key" doit obligatoirement exister
    {
        $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
        return false;
    }

    if (!isset($_POST['key'])) // le formulaire doit contenir le champ "key"
    {
        $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
        return false;
    }

    $secretKey = sha1($_SESSION['key'] . $this->salt);
    if ($_POST['key'] != $secretKey) // la clé secrète envoyée doit correspondre exactement à celle créée par la fonction
    {
        $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
        return false;
    }

    return true;
}

En dehors de la class, nous avons donc quelque chose du genre
PHP:
$class     = new SubmitForm();
$secretKey = $class->buildKey();

if ($_SERVER['REQUEST_METHOD'] == 'post') // on vérifie la clé seulement si la requête envoyée est au format POST
{
    $class->verifyKey();
}

PHP:
<?php

class SubmitForm
{
    public $salt   = '782hdbbab001mbdjbxaoi9';
    public $erreur = null;

    public function __construct()
    {
        session_start(); // on démarre la session
        $_SESSION['key'] = uniqid(microtime(true)); // on stocke notre clé relative au timestamp dans une variable de session
    }

    public function buildKey()
    {
        if (!isset($_SESSION['key']))
        {
            $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        $secretKey = sha1($_SESSION['key'] . $this->salt);
        return $secretKey;
    }

    public function verifyKey()
    {
        if (!isset($_SESSION['key'])) // la variable de session "key" doit obligatoirement exister
        {
            $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        if (!isset($_POST['key'])) // le formulaire doit contenir le champ "key"
        {
            $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        $secretKey = sha1($_SESSION['key'] . $this->salt);
        if ($_POST['key'] != $secretKey) // la clé secrète envoyée doit correspondre exactement à celle créée par la fonction
        {
            $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        return true;
    }
}

$class     = new SubmitForm();
$secretKey = $class->buildKey();

if ($_SERVER['REQUEST_METHOD'] == 'post') // on vérifie la clé seulement si la requête envoyée est au format POST
{
    $class->verifyKey();
}
?>

<!DOCTYPE html>
<html>
    <head>
        <!-- Vos données -->
    </head>
    <body>
        <?php
            if ($class->erreur)
            {
                echo $class->erreur;
            }
        ?>
        <form method="post" action="/">
            <input type="text" name="prenom" placeholder="Prénom..." />
            <input type="text" name="age" placeholder="Age..." />

            <input type="hidden" name="key" value="<?= $secretKey ?>" />
            <input type="submit" value="Soumettre" />
        </form>
    </body>
</html>

Je vous remercie d'avoir lu ce tutoriel, et n'hésitez pas à me faire part de vos erreurs / bugs rencontrés si vous utilisez le système que je viens de vous présenter ::cool::

Merci @Lawid SEC pour les headers :love:

Walky
Yeah, beau topic Walky ! ::):
 

Djamel SEC

Ancien staff
Inscription
24 Août 2012
Messages
19 637
Réactions
10 372
Points
27 570
    Réponse de Djamel SEC Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #3
Énorme Walky !
 

Ichigo' SEC

Commercial
Ancien staff
Inscription
24 Septembre 2011
Messages
6 644
Réactions
4 079
Points
25 620
    Réponse de Ichigo' SEC Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #4
Voir la pièce jointe 101360
Bonjour à tous , aujourd'hui nous allons, ensemble, apprendre à sécuriser nos formulaires HTML.

Voir la pièce jointe 101356
Bien évidemment, nous n'utiliserons pas de vérification Captcha ou ReCaptcha pour ne pas embêter le visiteur.

Le principe va consister à générer une clé secrète pour l'insérer dans un champ invisible dans notre formulaire.
Et lors de l'envoi du formulaire, nous allons vérifier la validité de la clé.

Pour générer notre clé secrètre, nous utiliserons deux paramètres:

  • Un salt (de préférence tapé à la main)
  • Le timestamp actuel
Veillez à ne pas utiliser de variables statiques, voilà pourquoi j'utilise le timestamp .

Comme vu dans la partie précédente, nous utiliserons deux paramètres, mais vous vous doutez bien qu'on ne les affichera pas directement dans le formulaire (même en champ masqué), on va donc utiliser une fonction PHP permettant de crypter les données , dans ce tutoriel je vais utiliser SHA1.

Commençons donc par créer notre seul et unique fichier, qui contiendra le formulaire HTML ainsi que le code PHP .


Je tiens à vous informer que j'utiliserai la POO tout au long du tutoriel.
PHP:
<?php

class SubmitForm
{
    public $salt   = '782hdbbab001mbdjbxaoi9'; // tapé à la main
    public $erreur = null; // ici, sera stocké l'erreur

    public function __construct()
    {
        session_start(); // on démarre la session
        $_SESSION['key'] = uniqid(microtime(true)); // on stocke notre clé relative au timestamp dans une variable de session
    }

    public function buildKey()
    {
        if (!isset($_SESSION['key'])) // la variable de session "key" doit obligatoirement exister
        {
            $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        $secretKey = sha1($_SESSION['key'] . $this->salt);
        return $secretKey;
    }
}

On constate donc qu'il y a une variable de class: $salt, contenant notre salt, ainsi que 2 fonctions. L'une, exécutée directement lors du chargement de la page, et une autre permettant de générer la clé secrète .

À cela on va ajouter le formulaire HTML , de base un formulaire non sécurisé ressemble à ceci:
HTML:
<!DOCTYPE html>
<html>
    <head>
        <!-- Vos données -->
    </head>
    <body>
        <form method="post" action="/">
            <input type="text" name="prenom" placeholder="Prénom..." />
            <input type="text" name="age" placeholder="Age..." />

            <input type="submit" value="Soumettre" />
        </form>
    </body>
</html>

On va donc stocker notre clé secrète dans une variable, générée par notre fonction créée précédemment.

PHP:
$class     = new SubmitForm();
$secretKey = $class->buildKey();

Et l'insérer dans un champ invisible dans le formulaire HTML
PHP:
<input type="hidden" name="key" value="<?= $secretKey ?>" />

Il ne nous reste donc, seulement la vérification de la clé ! Et afficher l'erreur dans le formulaire HTML
PHP:
public function verifyKey()
{
    if (!isset($_SESSION['key'])) // la variable de session "key" doit obligatoirement exister
    {
        $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
        return false;
    }

    if (!isset($_POST['key'])) // le formulaire doit contenir le champ "key"
    {
        $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
        return false;
    }

    $secretKey = sha1($_SESSION['key'] . $this->salt);
    if ($_POST['key'] != $secretKey) // la clé secrète envoyée doit correspondre exactement à celle créée par la fonction
    {
        $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
        return false;
    }

    return true;
}

En dehors de la class, nous avons donc quelque chose du genre
PHP:
$class     = new SubmitForm();
$secretKey = $class->buildKey();

if ($_SERVER['REQUEST_METHOD'] == 'post') // on vérifie la clé seulement si la requête envoyée est au format POST
{
    $class->verifyKey();
}

PHP:
<?php

class SubmitForm
{
    public $salt   = '782hdbbab001mbdjbxaoi9';
    public $erreur = null;

    public function __construct()
    {
        session_start(); // on démarre la session
        $_SESSION['key'] = uniqid(microtime(true)); // on stocke notre clé relative au timestamp dans une variable de session
    }

    public function buildKey()
    {
        if (!isset($_SESSION['key']))
        {
            $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        $secretKey = sha1($_SESSION['key'] . $this->salt);
        return $secretKey;
    }

    public function verifyKey()
    {
        if (!isset($_SESSION['key'])) // la variable de session "key" doit obligatoirement exister
        {
            $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        if (!isset($_POST['key'])) // le formulaire doit contenir le champ "key"
        {
            $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        $secretKey = sha1($_SESSION['key'] . $this->salt);
        if ($_POST['key'] != $secretKey) // la clé secrète envoyée doit correspondre exactement à celle créée par la fonction
        {
            $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        return true;
    }
}

$class     = new SubmitForm();
$secretKey = $class->buildKey();

if ($_SERVER['REQUEST_METHOD'] == 'post') // on vérifie la clé seulement si la requête envoyée est au format POST
{
    $class->verifyKey();
}
?>

<!DOCTYPE html>
<html>
    <head>
        <!-- Vos données -->
    </head>
    <body>
        <?php
            if ($class->erreur)
            {
                echo $class->erreur;
            }
        ?>
        <form method="post" action="/">
            <input type="text" name="prenom" placeholder="Prénom..." />
            <input type="text" name="age" placeholder="Age..." />

            <input type="hidden" name="key" value="<?= $secretKey ?>" />
            <input type="submit" value="Soumettre" />
        </form>
    </body>
</html>

Je vous remercie d'avoir lu ce tutoriel, et n'hésitez pas à me faire part de vos erreurs / bugs rencontrés si vous utilisez le système que je viens de vous présenter ::cool::

Merci @Lawid SEC pour les headers :love:

Walky
Lourd ! :panic:
 

Espi0n

Membre Premium Retraité
Premium
Inscription
27 Août 2015
Messages
2 346
Réactions
1 121
Points
8 781
    Réponse de Espi0n Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #5
Pas Lourd :trollface:
 

xRwizz

Ancien staff
Inscription
12 Juin 2013
Messages
18 443
Réactions
5 764
Points
21 368
    Réponse de xRwizz Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #7
Voir la pièce jointe 101360
Bonjour à tous , aujourd'hui nous allons, ensemble, apprendre à sécuriser nos formulaires HTML.

Voir la pièce jointe 101356
Bien évidemment, nous n'utiliserons pas de vérification Captcha ou ReCaptcha pour ne pas embêter le visiteur.

Le principe va consister à générer une clé secrète pour l'insérer dans un champ invisible dans notre formulaire.
Et lors de l'envoi du formulaire, nous allons vérifier la validité de la clé.

Pour générer notre clé secrètre, nous utiliserons deux paramètres:

  • Un salt (de préférence tapé à la main)
  • Le timestamp actuel
Veillez à ne pas utiliser de variables statiques, voilà pourquoi j'utilise le timestamp .

Comme vu dans la partie précédente, nous utiliserons deux paramètres, mais vous vous doutez bien qu'on ne les affichera pas directement dans le formulaire (même en champ masqué), on va donc utiliser une fonction PHP permettant de crypter les données , dans ce tutoriel je vais utiliser SHA1.

Commençons donc par créer notre seul et unique fichier, qui contiendra le formulaire HTML ainsi que le code PHP .


Je tiens à vous informer que j'utiliserai la POO tout au long du tutoriel.
PHP:
<?php

class SubmitForm
{
    public $salt   = '782hdbbab001mbdjbxaoi9'; // tapé à la main
    public $erreur = null; // ici, sera stocké l'erreur

    public function __construct()
    {
        session_start(); // on démarre la session
        $_SESSION['key'] = uniqid(microtime(true)); // on stocke notre clé relative au timestamp dans une variable de session
    }

    public function buildKey()
    {
        if (!isset($_SESSION['key'])) // la variable de session "key" doit obligatoirement exister
        {
            $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        $secretKey = sha1($_SESSION['key'] . $this->salt);
        return $secretKey;
    }
}

On constate donc qu'il y a une variable de class: $salt, contenant notre salt, ainsi que 2 fonctions. L'une, exécutée directement lors du chargement de la page, et une autre permettant de générer la clé secrète .

À cela on va ajouter le formulaire HTML , de base un formulaire non sécurisé ressemble à ceci:
HTML:
<!DOCTYPE html>
<html>
    <head>
        <!-- Vos données -->
    </head>
    <body>
        <form method="post" action="/">
            <input type="text" name="prenom" placeholder="Prénom..." />
            <input type="text" name="age" placeholder="Age..." />

            <input type="submit" value="Soumettre" />
        </form>
    </body>
</html>

On va donc stocker notre clé secrète dans une variable, générée par notre fonction créée précédemment.

PHP:
$class     = new SubmitForm();
$secretKey = $class->buildKey();

Et l'insérer dans un champ invisible dans le formulaire HTML
PHP:
<input type="hidden" name="key" value="<?= $secretKey ?>" />

Il ne nous reste donc, seulement la vérification de la clé ! Et afficher l'erreur dans le formulaire HTML
PHP:
public function verifyKey()
{
    if (!isset($_SESSION['key'])) // la variable de session "key" doit obligatoirement exister
    {
        $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
        return false;
    }

    if (!isset($_POST['key'])) // le formulaire doit contenir le champ "key"
    {
        $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
        return false;
    }

    $secretKey = sha1($_SESSION['key'] . $this->salt);
    if ($_POST['key'] != $secretKey) // la clé secrète envoyée doit correspondre exactement à celle créée par la fonction
    {
        $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
        return false;
    }

    return true;
}

En dehors de la class, nous avons donc quelque chose du genre
PHP:
$class     = new SubmitForm();
$secretKey = $class->buildKey();

if ($_SERVER['REQUEST_METHOD'] == 'post') // on vérifie la clé seulement si la requête envoyée est au format POST
{
    $class->verifyKey();
}

PHP:
<?php

class SubmitForm
{
    public $salt   = '782hdbbab001mbdjbxaoi9';
    public $erreur = null;

    public function __construct()
    {
        session_start(); // on démarre la session
        $_SESSION['key'] = uniqid(microtime(true)); // on stocke notre clé relative au timestamp dans une variable de session
    }

    public function buildKey()
    {
        if (!isset($_SESSION['key']))
        {
            $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        $secretKey = sha1($_SESSION['key'] . $this->salt);
        return $secretKey;
    }

    public function verifyKey()
    {
        if (!isset($_SESSION['key'])) // la variable de session "key" doit obligatoirement exister
        {
            $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        if (!isset($_POST['key'])) // le formulaire doit contenir le champ "key"
        {
            $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        $secretKey = sha1($_SESSION['key'] . $this->salt);
        if ($_POST['key'] != $secretKey) // la clé secrète envoyée doit correspondre exactement à celle créée par la fonction
        {
            $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        return true;
    }
}

$class     = new SubmitForm();
$secretKey = $class->buildKey();

if ($_SERVER['REQUEST_METHOD'] == 'post') // on vérifie la clé seulement si la requête envoyée est au format POST
{
    $class->verifyKey();
}
?>

<!DOCTYPE html>
<html>
    <head>
        <!-- Vos données -->
    </head>
    <body>
        <?php
            if ($class->erreur)
            {
                echo $class->erreur;
            }
        ?>
        <form method="post" action="/">
            <input type="text" name="prenom" placeholder="Prénom..." />
            <input type="text" name="age" placeholder="Age..." />

            <input type="hidden" name="key" value="<?= $secretKey ?>" />
            <input type="submit" value="Soumettre" />
        </form>
    </body>
</html>

Je vous remercie d'avoir lu ce tutoriel, et n'hésitez pas à me faire part de vos erreurs / bugs rencontrés si vous utilisez le système que je viens de vous présenter ::cool::

Merci @Lawid SEC pour les headers :love:

Walky
Du lourd, beau topic Walky ::cool::
 

ॐ Devkush ॐ

Premium
Inscription
30 Octobre 2015
Messages
588
Réactions
218
Points
2 176
    Réponse de ॐ Devkush ॐ Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #8
100% Fonctionelle merci pour ce tuto ;)
 

❤cœur

Le plus beau
Inscription
21 Juin 2014
Messages
1 171
Réactions
384
Points
4 788
    Réponse de ❤cœur Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #9
Voir la pièce jointe 101360
Bonjour à tous , aujourd'hui nous allons, ensemble, apprendre à sécuriser nos formulaires HTML.

Voir la pièce jointe 101356
Bien évidemment, nous n'utiliserons pas de vérification Captcha ou ReCaptcha pour ne pas embêter le visiteur.

Le principe va consister à générer une clé secrète pour l'insérer dans un champ invisible dans notre formulaire.
Et lors de l'envoi du formulaire, nous allons vérifier la validité de la clé.

Pour générer notre clé secrètre, nous utiliserons deux paramètres:

  • Un salt (de préférence tapé à la main)
  • Le timestamp actuel
Veillez à ne pas utiliser de variables statiques, voilà pourquoi j'utilise le timestamp .

Comme vu dans la partie précédente, nous utiliserons deux paramètres, mais vous vous doutez bien qu'on ne les affichera pas directement dans le formulaire (même en champ masqué), on va donc utiliser une fonction PHP permettant de crypter les données , dans ce tutoriel je vais utiliser SHA1.

Commençons donc par créer notre seul et unique fichier, qui contiendra le formulaire HTML ainsi que le code PHP .


Je tiens à vous informer que j'utiliserai la POO tout au long du tutoriel.
PHP:
<?php

class SubmitForm
{
    public $salt   = '782hdbbab001mbdjbxaoi9'; // tapé à la main
    public $erreur = null; // ici, sera stocké l'erreur

    public function __construct()
    {
        session_start(); // on démarre la session
        $_SESSION['key'] = uniqid(microtime(true)); // on stocke notre clé relative au timestamp dans une variable de session
    }

    public function buildKey()
    {
        if (!isset($_SESSION['key'])) // la variable de session "key" doit obligatoirement exister
        {
            $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        $secretKey = sha1($_SESSION['key'] . $this->salt);
        return $secretKey;
    }
}

On constate donc qu'il y a une variable de class: $salt, contenant notre salt, ainsi que 2 fonctions. L'une, exécutée directement lors du chargement de la page, et une autre permettant de générer la clé secrète .

À cela on va ajouter le formulaire HTML , de base un formulaire non sécurisé ressemble à ceci:
HTML:
<!DOCTYPE html>
<html>
    <head>
        <!-- Vos données -->
    </head>
    <body>
        <form method="post" action="/">
            <input type="text" name="prenom" placeholder="Prénom..." />
            <input type="text" name="age" placeholder="Age..." />

            <input type="submit" value="Soumettre" />
        </form>
    </body>
</html>

On va donc stocker notre clé secrète dans une variable, générée par notre fonction créée précédemment.

PHP:
$class     = new SubmitForm();
$secretKey = $class->buildKey();

Et l'insérer dans un champ invisible dans le formulaire HTML
PHP:
<input type="hidden" name="key" value="<?= $secretKey ?>" />

Il ne nous reste donc, seulement la vérification de la clé ! Et afficher l'erreur dans le formulaire HTML
PHP:
public function verifyKey()
{
    if (!isset($_SESSION['key'])) // la variable de session "key" doit obligatoirement exister
    {
        $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
        return false;
    }

    if (!isset($_POST['key'])) // le formulaire doit contenir le champ "key"
    {
        $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
        return false;
    }

    $secretKey = sha1($_SESSION['key'] . $this->salt);
    if ($_POST['key'] != $secretKey) // la clé secrète envoyée doit correspondre exactement à celle créée par la fonction
    {
        $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
        return false;
    }

    return true;
}

En dehors de la class, nous avons donc quelque chose du genre
PHP:
$class     = new SubmitForm();
$secretKey = $class->buildKey();

if ($_SERVER['REQUEST_METHOD'] == 'post') // on vérifie la clé seulement si la requête envoyée est au format POST
{
    $class->verifyKey();
}

PHP:
<?php

class SubmitForm
{
    public $salt   = '782hdbbab001mbdjbxaoi9';
    public $erreur = null;

    public function __construct()
    {
        session_start(); // on démarre la session
        $_SESSION['key'] = uniqid(microtime(true)); // on stocke notre clé relative au timestamp dans une variable de session
    }

    public function buildKey()
    {
        if (!isset($_SESSION['key']))
        {
            $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        $secretKey = sha1($_SESSION['key'] . $this->salt);
        return $secretKey;
    }

    public function verifyKey()
    {
        if (!isset($_SESSION['key'])) // la variable de session "key" doit obligatoirement exister
        {
            $this->erreur = 'Une erreur s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        if (!isset($_POST['key'])) // le formulaire doit contenir le champ "key"
        {
            $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        $secretKey = sha1($_SESSION['key'] . $this->salt);
        if ($_POST['key'] != $secretKey) // la clé secrète envoyée doit correspondre exactement à celle créée par la fonction
        {
            $this->erreur = 'Une erreur de sécurité s\'est produite, veuillez rafraîchir la page.';
            return false;
        }

        return true;
    }
}

$class     = new SubmitForm();
$secretKey = $class->buildKey();

if ($_SERVER['REQUEST_METHOD'] == 'post') // on vérifie la clé seulement si la requête envoyée est au format POST
{
    $class->verifyKey();
}
?>

<!DOCTYPE html>
<html>
    <head>
        <!-- Vos données -->
    </head>
    <body>
        <?php
            if ($class->erreur)
            {
                echo $class->erreur;
            }
        ?>
        <form method="post" action="/">
            <input type="text" name="prenom" placeholder="Prénom..." />
            <input type="text" name="age" placeholder="Age..." />

            <input type="hidden" name="key" value="<?= $secretKey ?>" />
            <input type="submit" value="Soumettre" />
        </form>
    </body>
</html>

Je vous remercie d'avoir lu ce tutoriel, et n'hésitez pas à me faire part de vos erreurs / bugs rencontrés si vous utilisez le système que je viens de vous présenter ::cool::

Merci @Lawid SEC pour les headers :love:

Walky
Premier Developpédacteur ?
 

WhiiTe'

Administateur
Ancien staff
Inscription
22 Octobre 2011
Messages
14 613
Réactions
8 473
Points
30 925
    Réponse de WhiiTe' Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #11
BG Walky ! :cool:
 

Insomniaque97

Premium
Inscription
21 Juillet 2015
Messages
1 094
Réactions
507
Points
10 335
    Réponse de Insomniaque97 Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #13
Merci beaucoup, très intéressant !
 

Rivals

Ancien staff
Inscription
27 Août 2016
Messages
1 690
Réactions
890
Points
11 104
    Réponse de Rivals Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #14
Bonjour Walky SEC ,

Je ne veux pas être méchant mais ça ne sécurise en rien ton formulaire à l'heure d'aujourd'hui, avec par exemple on peut très facilement spammer ton formulaire et rendre ton token inutile :p

PHP:
public $erreur = null;

Equivaut à :
PHP:
public $erreur;

Et le salt doit avoir une portée limitée donc protected ;)

Presque parfait :trollface:

P.S : Tu as oublié de charger ta classe

Bonne journée,
Rivals
 

Walky 🇫🇷

Cryptoboy
Ancien staff
Inscription
18 Octobre 2012
Messages
1 268
Réactions
1 187
Points
17 650
    Réponse de Walky 🇫🇷 Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #16
P.S : Tu as oublié de charger ta classe
PHP:
$class = new SubmitForm();
:d:

Je ne vois pas comment PhantomJS pourrait "bypass" le formulaire, sachant que si la clé n'est pas valide / non définie, le formulaire ne s'envoie pas (je prends le cas ou les données du formulaire seraient sauvegardées etc..)
 

Rivals

Ancien staff
Inscription
27 Août 2016
Messages
1 690
Réactions
890
Points
11 104
    Réponse de Rivals Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #17
PHP:
$class = new SubmitForm();
:d:

Je ne vois pas comment PhantomJS pourrait "bypass" le formulaire, sachant que si la clé n'est pas valide / non définie, le formulaire ne s'envoie pas (je prends le cas ou les données du formulaire seraient sauvegardées etc..)
C'est pas ça charger, ça c'est instancier (tu dois require ton fichier) :d:

PhantomJS te permet de toucher au DOM, donc avoir accès à ton input caché et ainsi on peut faire des boucles :p
 

Walky 🇫🇷

Cryptoboy
Ancien staff
Inscription
18 Octobre 2012
Messages
1 268
Réactions
1 187
Points
17 650
    Réponse de Walky 🇫🇷 Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #18
C'est pas ça charger, ça c'est instancier (tu dois require ton fichier) :d:
Le code HTML et PHP sont dans le même fichier, donc pas besoin :)

PhantomJS te permet de toucher au DOM, donc avoir accès à ton input caché et ainsi on peut faire des boucles :p
Hum, oui je vois un peu près le fonctionnement :mmh:

Enfin bon, ça permet toujours de sécuriser un minimum ses formulaires, contrairement à un formulaire sans clé.
 

Rivals

Ancien staff
Inscription
27 Août 2016
Messages
1 690
Réactions
890
Points
11 104
    Réponse de Rivals Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #19
Le code HTML et PHP sont dans le même fichier, donc pas besoin :)


Hum, oui je vois un peu près le fonctionnement :mmh:

Enfin bon, ça permet toujours de sécuriser un minimum ses formulaires, contrairement à un formulaire sans clé.
Ah d'accord, je pensais que tu séparais les deux, good job :neo:
 

ian ?

Premium
Inscription
7 Novembre 2016
Messages
218
Réactions
102
Points
756
    Réponse de ian ? Informatique et nouvelles technologies Développement : Sécurisez vos formulaires - PHP
  • #20
Lourd merci beaucouè
 

Discussions similaires


Haut Bas