[RESOLU] fetch vs fetchAll problème ARRAY

Eléphanteau du PHP | 25 Messages

19 nov. 2022, 12:58

Hello all,

J'ai une fonction qui doit me retourner toutes les lignes correspondantes à la requête
=> je me dis alors qu'il me faut utiliser fetchALL (PDO :: FETCH_ASSOC) afin de recevoir les lignes ET le nom de la colonne

Car le but c'est de remplir un tableau pour présenter les résultats.

SAUF QUE :
Quand j'utilise fetch je n'ai aucun soucis pour afficher une ligne avec les en-têtes mais quand j'utilise fetchAll j'ai un pb de : Notice: Array to string conversion et en plus je n'ai pas les bonnes en-têtes...

Je ne comprends pas et ça m'énerve :(

Voici la fonction :
// fonction qui permet de faire une requête dans la DB sur le morceau que l'on recherche
function rechercheTab() {
    $conn = connectionDB();
    $query = 'SELECT * FROM aebersold WHERE titre LIKE "' . $_POST['titre'] . '%" ORDER BY titre';
    $stmt = $conn->query($query);

    $donnees = $stmt->fetch(PDO::FETCH_ASSOC);
    return $donnees;
}
Voici la page d'affichage :
<?php
require_once 'functions.php';
include 'menu.php';
include 'header.php';

echo '<br>';

//Formulaire de recherche des morceaux
echo '
    <form action="#" method="post">
        <label for="titre">Titre recherché : </label><input type="text" id="titre" name="titre">
        <input type="submit" value="Envoyer">
        <br><hr>';

// Debut du tableau
echo '<table><thead><tr>';

//On remplit le tableau grâce à la fonction rechercheTab
if (isset($_POST['titre'])) {
    $donnees = rechercheTab();
    foreach ($donnees as $key => $donnee) {

        echo '<th>' . $key . ' </th>'; //j'affiche les en-têtes de ma DB

    }
    echo '</tr></thead><tbody><tr>';
    foreach ($donnees as $key => $donnee) {

        echo '<td>' . $donnee . ' </td>'; //je remplis le tableau avec les données de ma DB

    }
    echo '</tr></tbody></table>';
}

include 'footer.php';
?>
Quelqu'un peut il m'expliquer ce que je ne comprends pas svp :)

Merci

ynx
Mammouth du PHP | 586 Messages

19 nov. 2022, 17:36

Bonjour,

La méthode fetch retourne une seule ligne du résultat sous la forme d'un tableau associatif (si PDO::FETCH_ASSOC) que tu peux parcourir via une boucle comme tu le fais actuellement.

La méthode fetchAll retourne toutes les lignes du résultat sous la forme d'un tableau, chaque élément de ce tableau est un tableau associatif correspondant à une ligne.

Il faut donc que tu fasse une première boucle pour parcourir les résultats récupérés avec fetchAll, et une 2e boucle dans la première pour chaque résultat comme ton code actuel.

Eléphanteau du PHP | 25 Messages

19 nov. 2022, 21:29

Tout d'abord merci pour ton aide, j'apprécie.

J'avais donc bien compris la différence entre les 2, ça me rassure.
En revanche je vois pas trop comment faire 2 boucles... en fait je ne vois pas sur quoi boucler avec la deuxième :(

Le premier foreach me donne :
[nom de ma colonne] => contenu de la colonne

du coup si je comprends bien je dois refaire la même boucle pour remplir le tableau ?

Eléphanteau du PHP | 25 Messages

19 nov. 2022, 21:58

Voilà où j'en suis :
<?php
require_once 'functions.php';
include 'menu.php';
include 'header.php';

echo '<br>';

//Formulaire de recherche des morceaux
echo '
    <form action="#" method="post">
        <label for="titre">Titre recherché : </label><input type="text" id="titre" name="titre">
        <input type="submit" value="Envoyer">
        <br><hr>';

// Debut du tableau
echo '<table><thead><tr>';

//On remplit le tableau grâce à la fonction rechercheTab
if (isset($_POST['titre'])) {
    $datas = rechercheTab();
    foreach ($datas as $data) {

        foreach ($data as $colonne => $contenu) {

            echo '<th>' . $colonne . ' </th>'; //j'affiche les en-têtes de ma DB

        }
        echo '</tr></thead><tbody><tr>';
        foreach ($data as $colonne => $contenu) {
            echo '<td>' . $contenu . ' </td>'; //je remplis le tableau avec les données de ma DB
        }
        // echo '</tr></tbody>';

    }

}
//echo '</tr></thead>';
//echo '</tr></tbody></table>';
echo '</table>';

include 'footer.php';
?>
ça commence à ressembler à quelque chose mais du coup j'ai la requête trouve 2 entrées j'ai 2 fois les en-têtes :(

Pas évident de comprendre comment ça fonctionne exactement ces tableaux.. je vais creuser encore un peu plus car je croyais avoir compris :(

Mammouth du PHP | 2703 Messages

19 nov. 2022, 22:50

pour afficher les entêtes, il ne faut pas faire une boucle sur toutes les lignes, juste récupérer les données de la première ligne.
ou plus simple, coder la ligne d'entête en dur, ce qui permet de mettre des intitulés de colonne différents de ceux de la table.

Eléphanteau du PHP | 25 Messages

19 nov. 2022, 23:56

Bon voilà j'y suis :)
<!-- Formulaire de recherche des morceaux -->

    <form action="#" method="post">
        <label for="titre">Titre recherché : </label><input type="text" id="titre" name="titre">
        <input type="submit" value="Envoyer">
        <br><hr>

<!-- Debut du tableau -->
<table>
    <thead>
        <tr>
            <th>Id</th>
            <th>Titre</th>
            <th>Volume</th>
            <th>Vehicle</th>
            <th>Key</th>
            <th>Tempo</th>
            <th>Chorus</th>
            <th>Disc</th>
            <th>Track</th>
        </tr>
    </thead>
    <tbody>
        <tr>

<?php
//On remplit le tableau grâce à la fonction rechercheTab
if (isset($_POST['titre'])) {
    $datas = rechercheTab();
    foreach ($datas as $data) {
        foreach ($data as $colonne => $contenu) {
            echo '<td>' . $contenu . ' </br></td>'; //je remplis le tableau avec les données de ma DB
        }
        echo '</tr></tbody>';
    }
}
?>
</table>
J'avais fait une 1ere version ou tt était en HTML et du coup j'écrivais chaque ligne avec un boucle FOREACH mais je trouvais ça pas top.
En voulant réécrire en PHP je me suis retrouve confronté à ce pb de boucle...

Bon finalement je pense avoir compris.

Maintenant je vais chercher comment rendre une colonne cliquable pour afficher des infos sur le morceau.... bref je suis pas couché :)

Merci à tous,
Steph