PDO insert ne fonctionnant pas

Default
,

Bonjour,

Je suis nouveau en programmation.

Voila je rencontre un petit problème avec mon code.

Formulaire d'inscription dans BDD via PDO

J'ai 2 fichiers:
un fichier database.inc.php contenant que ce bout de code:
<?php
$recettes = new PDO('mysql:dbname=testdb;dbname=recettes;host=127.0.0.1;charset=utf8mb4', 'root', '');
?>

et un fichier subscribe.php:
`
<?php

//Les inc
include("inc/header.inc.php");
include_once("inc/timer.inc.php");
include_once("inc/database.inc.php");

// Test si remplissage et sécurité filter_input

if (isset($_POST['formSubcription'])) {
$loginSub = filter_input(INPUT_POST,'loginSub');
$prenom = filter_input(INPUT_POST,'prenom');
$nom = filter_input(INPUT_POST,'nom');
//prise de sha1, pas md5, test
$passwordSub = sha1($_POST['passwordSub']);
$passwordSub2 = sha1($_POST['passwordSub2']);

if (!empty($_POST['loginSub']) and !empty($_POST['prenom']) and !empty($_POST['nom']) and !empty($_POST['passwordSub'])) {

    $loginSublength = strlen($loginSub);
    if ($loginSublength >= 4 and $loginSublength <= 10) {

        $reqloginSub = $cooking->prepare("SELECT * FROM membres WHERE loginSub = ?)");
        $reqloginSub->execute(array($loginSub));
        //Test si loginSub existe
        $loginSubexists = $reqloginSub->rowCount();


        if ($loginSubexists == 0) {
            if ($passwordSub2 == $passwordSub) {

                $subcription = $recettes->prepare("INSERT INTO membres ('idMembre,gravatar,login,password,statut,prenom,nom,dateCrea') VALUES (?,?,?,?,?,?,?,NOW())");
                $subcription->execute(array('','','',$loginSub, $passwordSub,'membre', $prenom, $nom,''));

                header('Location: profile.php');

            } else {
                $erreur = "Les mots de passe ne correspondent pas";
            }
        } else {
            $erreur = "Le login est déjà utilisé";
        }
    } else {
        $erreur = "Votre login doit être compris entre 5 et 10 caractères";
    }
} else {
    $erreur = "Tous les champs doivent être remplis";}

}

?>

<!Doctype html>


Enregistrement





<!-- 1- Bootstrap-->
<link rel="stylesheet" href="css/bootstrap-grid.min.css">
<link rel="stylesheet" href="css/bootstrap.min.css">

<!-- 2- Mes feuilles de style-->
<link rel="stylesheet" type="text/css" href="css/style.css">


Accueil



                <label for="loginSub">login</label>
                <input type="text" name="loginSub" id="loginSub" placeholder="login"><br><br>

                <label for="prenom">Prenom</label>
                <input type="text" name="prenom" id="prenom" placeholder="prenom"><br><br>

                <label for="nom">Nom</label>
                <input type="text" name="nom" id="nom" placeholder="nom"><br><br>

                <label for="passwordSub">Mot de Passe</label>
                <input type="password" name="passwordSub" id="passwordSub" placeholder="Mot de Passe"><br><br>

                <label for="passwordSub2">Confirmation Mot de Passe</label>
                <input type="password" name="passwordSub2" id="passwordSub2" placeholder="Confirmation Mot de Passe"><br><br>

                <input type="submit" name = "formSubcription" value="S'enregistrer">

            </form>
        </div>
    </div>
</div>

<!-- Vérification sécurité htmlspecialchars et htmlentities-->

<?php

// Vérification erreur formulaire
if (isset($erreur)) {
echo $erreur;
}

//footer
include("inc/footer.inc.php");
?>


`

Ce formulaire servirait à insérer des utilisateurs dans une BDD

J'aimerais que ce formulaire insère des utilisateurs dans ma bdd 'membres" (avec vérification que le login n'ait pas déjà été utilisé).
=> Seulement, ce formulaire ne permet de remplir que le login, nom, prénom et mot de passe alors que ma table comporte plus de champs.

Ce que j'obtiens

L'insertion ne se fait pas mais je suis bien redirigé vers profile.php grace au header('location: profile.php');
Pourtant quand je teste via un SELECT * FROM membres ou un var_dump, les infos s'affichent.

Voyez vous un élément qui fait que ca ne marche pas et que j'aurais zappé?

D'avance merci et bonnes fêtes.

9 Réponse

17162
,

Bonsoir.
Tu as deux principales erreurs.
La première se situe dans ta requête de sélection, tu as une parenthèse fermante qui n'a rien à y faire :

SELECT * FROM membres WHERE loginSub = ?) // Juste ici

La seconde concerne le nombre de paramêtre dans ta requête d'insertion.
Dans les noms de colonnes tu en passe 8, dans les valeurs à y insérer il y en a 8 dont 7 à passer dans la méthode execute, jusque là pas de soucis.
Mais, dans la méthode execute, tu envois 9 valeurs en paramêtres, alors que tu ne devrais en passer que 7.

L'insertion ne se fait pas mais je suis bien redirigé vers profile.php grace au header('location: profile.php');

Ce n'est pas parce que tu es redirigé que la requête SQL s'effectue.
Si la redirection s'effectue, c'est tout simplement que ta redirection se situe dans la partie qui a permis toutes les vérifications concernant ta validation du formulaire, donc la validation est correcte mais ce n'est pas le cas pour ta requête d'insertion.
PDO ne va pas stopper le code qui suit si tu ne l'a pas configuré pour qu'il renvoie une erreur à la moindre erreur dans tes requêtes SQL.
Autre chose aussi, dans ta première requête SQL tu utilise l'object PDO via une variable qui porte le nom cooking, mais pour la seconde tu utilises une variable qui porte le nom recettes, alors qu'entre les deux je ne vois pas à quel moment tu définies la seconde et je ne comprends pas non plus pourquoi tu aurais besoin d'en changer le nom entre les deux requêtes.

Default
,

Hello Lartak,

Merci de ta réponse rapide.
Tu as raison, j'ai laissé plein de fautes de distraction dont l'espace derrière la requête.

Pour le nombre de paramètres, je viens de changer pour cela:
$subcription = $cooking->prepare("INSERT INTO membres ('idMembre,gravatar,login,password,statut,prenom,nom,dateCrea') VALUES (?,?,?,?,?,?,?,NOW())");
$subcription->execute(array('','',$loginSub, $passwordSub,'membre', $prenom, $nom));

Mais ne vois toujours pas d'insertion dans ma base de données.

Concernant le nom de la variable, c'est aussi une étourderie. Quand j'ai copié mon code sur le site, j'ai renommé ma variable à la volée pour éviter de me faire repérer par mon prof (s'il venait à aller sur ce site :) )

Je dois relire mon code. Je les trouverais ces erreurs.
Très bon réveillon à toi :)

40917
,

Bonjour,
idMembre est à mon avis en auto-increment donc il ne faut pas le spécifier dans la requête.
De plus si tu mets gravatar à null par défaut, tu n'auras pas non plus besoin de le spécifier dans la requête.

Enfin au vu du nombre de paramètre dans la requête, je te conseil de passer par des "marqueurs nommées"

$req = $bdd->prepare("INSERT INTO ..... (login, pwd ) VALUES ( :login, :pwd)");
$req->execute(array(":login" => $login, ":pwd" => $pwd));
Default
,

Hello Carouge10, j'avais essayé ta méthode et d'autres mais ai maintenant une erreur.
Comme gravatar ne peut être à NULL, j'ai forcé gravatar à avoir une image.
Je ne suis vraiment pas sûr de mon code (c'est peu de le dire) :

`<?php
$subcription = $cooking->prepare("INSERT INTO membres ('gravatar,login,password,statut,prenom,nom,dateCrea') VALUES ('default.png',:login,:password,'membre',:prenom,:nom,NOW");

$subcription->execute(array(":login"=> $loginSub, ":password"=> $passwordSub, ":prenom"=> $prenom, ":nom"=> $nom))
?>`

D'avance merci de votre aide

40917
,

l'erreur est ......
Enlève le quote ' avant gravatar et le quote ' après dateCrea

17162
,

Pourquoi est-ce que ton listing de champs est entouré de quotes ? ('gravatar,login,password,statut,prenom,nom,dateCrea')

Default
,

Hello Carouge10 et Lartak, merci d'être au taquet :)
J'avais mis entre quote les champs car étant donné que les champs 'login' et 'password' semblaient être des variables 'interdites' et apparaissaient en bleu sur Visual Studio, je voulais éviter une erreur.

Maintenant, j'ai une erreur (Fatal error: PDOException:) sur la ligne de l'execute (ligne 31).
J'ai lu que pour certains, cela serait dû au nombre inégal de paramètres attendus et de paramètres déclarés.
Je ne vois pas ce que j'aurais zappé.
Etant donné que gravatar prend une valeur par défaut et que dateCrea prend la valeur NOW, je ne les ai pas déclaré en paramètres à la ligne de l'execute (ligne 31).

Est ce qu'il serait possible de vous montrer le code?
Je viens de copier sur codeshare:
https://codeshare.io/5ox4rM

Quand je fais ces mêmes manip sur phpmyadmin en mettant:
INSERT INTO membres (gravatar,login,password,statut,prenom,nom,dateCrea) VALUES ('default.png','test','test,'test','test','test',NOW");
L'insertion se fait correctement.

Merci encore :)

40917
,

Relis-toi, il manque une ) après NOW et now est une fonction donc il lui faut ses parentèses

Default
,

Merci Carouge! Je les avais bêtement supprimé quand j'étais sur phpmyadmin :)
Ca fonctionne :)