(ORDER BY) impossible de trier une liste avec un ORDER BY [Résolu]

Signaler
-
Messages postés
16136
Date d'inscription
lundi 9 juin 2008
Statut
Contributeur
Dernière intervention
24 juin 2021
-
Bonjour,

J'ai un code avec lequel je n'arrive pas à trier avec un ORDER BY. J'ai trois champs, le champ nom du produit, le champ mois et le champ année, par rapport aux recherches que je fais, tous mes ORDER BY fonctionnent sauf mon ORDER BY lié au nom de mon produit,

voici mon code :

$requete = 'SELECT * from licenceseset WHERE 1=1';
			
			if (isset($_GET['nomProduit']) AND $_GET['nomProduit']!="tous"){
				$requete .= ' AND nomProduit LIKE"%'.$_GET['nomProduit'].'%"';
			}

			/*if (isset($_GET['licence']) AND ($_GET['licence'] == "expiremois")){
				$requete .= ' AND dateExpiration >= DATE(NOW() + INTERVAL 0 MONTH) AND dateExpiration <= DATE(NOW() + INTERVAL 1 MONTH)';
			}*/

			if ($_GET['moisSelec'] != "all" AND $_GET['annee'] == "ALL" ){
				$requete .= ' AND MONTH(dateExpiration) = '.$_GET["moisSelec"].' ORDER BY dateExpiration ASC';
			}


			if ($_GET['moisSelec'] != "all" AND $_GET['annee'] != "ALL" ){
				$requete .= ' AND MONTH(dateExpiration) = '.$_GET["moisSelec"].' AND YEAR(dateExpiration) = '.$_GET["annee"].' ORDER BY dateExpiration ASC';
			}

			if ($_GET['moisSelec'] == "all" AND $_GET['annee'] != "ALL" ){
				$requete .= ' AND  YEAR(dateExpiration) = '.$_GET["annee"].' ORDER BY dateExpiration ASC';
			}




			$stmt = $pdo->prepare($requete);
			$stmt->execute();
			$resu = $stmt->fetchALL();

6 réponses

Messages postés
33031
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
24 juin 2021
3 580
Bonjour,

Pour commencer.. fais donc un echo de ta variable $requete et regarde ce qu'elle contient.
Sert toi du résultat obtenu pour tester la requête DIRECTEMENT dans ta bdd ( via l'onglet requête de PHPMYADMIN ) et ainsi t'assurer que ta requête fonctionne...

Au passage, vu que tu utilises PDO, merci d'appliquer ceci :
https://www.commentcamarche.net/faq/46512-pdo-gerer-les-erreurs

Ainsi que ça
https://www.commentcamarche.net/faq/48399-php-gestion-des-erreurs-debogage-et-ecriture-du-code
J'ai testé et ma requête fonctionne, le seul truc qui fais que mon ORDER BY ne fonctionne pas seulement pour le nom de produit c'est le
LIKE"%'.$_GET['nomProduit'].'%"';
. Avec le LIKE je n'arrive pas à appliquer le ORDER BY alors que dans le reste du code ou le LIKE n'existe pas et est remplacé par un =, le ORDER BY fonctionne mais si je remplace le LIKE par un =, ma page ne s'affiche plus :/
Messages postés
16136
Date d'inscription
lundi 9 juin 2008
Statut
Contributeur
Dernière intervention
24 juin 2021
869
bonjour, quel résultat obtiens-tu quand "ORDER BY ne fonctionne pas"?
Si je met le ORDER BY juste après le LIKE, le ORDER BY fonctionne pour le nom de produit et la recherche fonctionne aussi si on met n'importe quel nom de produit mais dès que je rentre une année ou un mois dans la barre de recherche, plus rien ne s'affiche, ça me dit qu'aucune licence ne correspond à ce résultat pour toutes les années et tous les mois, en gros si je met le ORDER BY après le LIKE, ma recherche ne fonctionne seulement pour le nom de produit.
> antho
Et si je le met à la fin de tous mes if j'ai :
SELECT * from licenceseset WHERE 1=1 AND MONTH(dateExpiration) = AND YEAR(dateExpiration) = ORDER BY dateExpiration ASC
Messages postés
16136
Date d'inscription
lundi 9 juin 2008
Statut
Contributeur
Dernière intervention
24 juin 2021
869 > antho
c'est, bien sûr, juste avant le prepare() qu'il faut afficher la requete.

comme tu le vois, ta requête est incorrecte:
SELECT * from licenceseset 
WHERE 1=1 
AND MONTH(dateExpiration) = 
AND YEAR(dateExpiration) = 
ORDER BY dateExpiration ASC


as-tu testé cette requête dans phpmyadmin?
>
Messages postés
16136
Date d'inscription
lundi 9 juin 2008
Statut
Contributeur
Dernière intervention
24 juin 2021

Je vous avourez que je suis en 1ere année d'alternance et que je galère pas mal sur le php en ce moment :// et du coup non je n'ai pas essayé dans php my admin, que puis-je faire du coup pour régler ce problème ?
Messages postés
33031
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
24 juin 2021
3 580 > antho
Et.... tu ne vois pas une erreur ????
Il te manque un truc avant le "ORDER" ... juste après le "=" ... non ??
>
Messages postés
33031
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
24 juin 2021

Désolé mais je vois pas... je débute..

Surtout que je comprend pas parce que dans les requête où j'ai les =, le ORDER BY fonctionne, il y a que là où j'ai le LIKE"% que mon ORDER BY ne fonctionne pas :/

Excusez-moi, c'est peut être un truc tout con et vous allez penser que je suis inculte mais comme je vous le dis, je débute seulement, je fais vraiment pas souvent de PHP pour l'instant..
Si je ne met pas le ORDER BY dans
$requete .= ' AND nomProduit LIKE"%'.$_GET['nomProduit'].'%"';
, la recherche fonctionne parfaitement mais les licences ne sont pas triées :/

Donc si je met le ORDER BY, la recherche ne fonctionne plus et si je ne le met pas, mes licences ne sont pas triées, c'est donc ça mon problème :/
Messages postés
33031
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
24 juin 2021
3 580
La clause ORDER BY doit se trouver A LA FIN de la requête
Après éventuellement toutes les conditions qui se situent dans le WHERE...

Pour voir ce qui ne fonctionne pas il serait bien :
1 - d'appliquer le contenu des liens que je t'ai donné
2 - Nous montrer le code corrigé ( en appliquant les liens que je t'ai donné )

3 - Que tu fasses un echo de ta variable $requete pour voir à quoi elle ressemble lorsque ça ne marche pas
3 bis - Que tu nous montres ce que te donne ton echo
3 ter - Que tu copies/colle cette requête ainsi récupérée directement dans ton phpmyadmin pour voir si elle fonctionne
Messages postés
33031
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
24 juin 2021
3 580
<?php

// récupération PROPRE des variables AVANT de les utiliser!
$nomProduit = !empty($_GET['nomProduit']) ? trim($_GET['nomProduit']) : NULL;
$annee = !empty($_GET['annee']) ? trim($_GET['annee']) : NULL;
$moisSelec = !empty($_GET['moisSelec']) ? trim($_GET['moisSelec']) : NULL;


// Préparation de la requête
$requete = 'SELECT * from licenceseset WHERE 1=1 ';
$orderBy = "";
$datas = array();
if ($nomProduit && $nomProduit != 'tous') {
  $requete .= ' AND nomProduit LIKE "%' . $nomProduit . '%"';
  $orderBy .= " nomProduit ASC ";
}

if ($moisSelec == 'all') {
  if ($annee != 'ALL') {
    $requete .= ' AND  YEAR(dateExpiration) = :annee ';
    $datas[':annee'] = $annee;
    $orderBy .= " dateExpiration ASC ";
  }
} else {
  if ($annee == 'ALL') {
    $requete .= ' AND MONTH(dateExpiration) = :moisSelec ';
    $datas[':moisSelect'] = $moisSelec;
    $orderBy .= " dateExpiration ASC ";
  } else {
    $requete .= ' AND MONTH(dateExpiration) = :moisSelec
      AND YEAR(dateExpiration) = :annee ';
    $datas[':moisSelect'] = $moisSelec;
    $datas[':annee'] = $annee;
    $orderBy .= " dateExpiration ASC ";
  }
}

if (!empty($orderBy)) {
  $requete .= ' ORDER BY ' . $orderBy;
}

//exécution PROPRE de la requête (dans un bloc TRY/CATCH )
try {
  $stmt = $pdo->prepare($requete);
  $stmt->execute($datas);
  $resu = $stmt->fetchAll();
} catch (Exception $e) {
  echo "Erreur dans la requete : " . $requete;
  echo "<br>" . $e->getMessage();
  echo "<br> DATAS : " . print_r($datas, true);
}


Merci pour le temps que tu as passé pour m'aider, mais j'ai pris ton code et avec ton code si je spécifie une année par exemple, ça me dit que aucune licence ne correspond et le tri ne se fait pas :/
Messages postés
33031
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
24 juin 2021
3 580 > antho
Il nous manque un certain nombre d'informations...
À commencer par le contenu des variable qui se trouve dans ton url...
Pourrais-tu faire un
 print_r($_GET);  

Au début de ton script PHP et nous montrer ce que ça donne ?

vu ton message d'erreur, il serait bien également de nous montrer l'intégralité de ton code... Y compris ton formulaire de recherche...
Messages postés
33031
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
24 juin 2021
3 580
J'en ai profité pour faire quelques corrections au code
<?php


var_dump($_GET);//le temps des tests 

// récupération PROPRE des variables AVANT de les utiliser!
$nomProduit = !empty($_GET['nomProduit']) ? trim($_GET['nomProduit']) : NULL;
$annee = !empty($_GET['annee']) ? trim($_GET['annee']) : NULL;
$moisSelec = !empty($_GET['moisSelec']) ? trim($_GET['moisSelec']) : NULL;


// Préparation de la requête
$requete = 'SELECT * from licenceseset WHERE 1=1 ';
$orderBy = array();
$datas = array();
if ($nomProduit && $nomProduit != 'tous') {
  $requete .= ' AND nomProduit LIKE "%' . $nomProduit . '%"';
  $orderBy[]= " nomProduit ASC ";
}

if ( $moisSelec == 'all') {
  if ($annee && $annee != 'ALL') {
    $requete .= ' AND  YEAR(dateExpiration) = :annee ';
    $datas[':annee'] = $annee;
    $orderBy[]= " dateExpiration ASC ";
  }
} elseif($moisSelec) {
  $requete .= ' AND MONTH(dateExpiration) = :moisSelec ';
   $datas[':moisSelect'] = $moisSelec;
  if($annee) {
    $requete .= ' AND YEAR(dateExpiration) = :annee ';
    $datas[':annee'] = $annee;
  }
   $orderBy[] = " dateExpiration ASC ";
}

if (!empty($orderBy)) {
  $requete .= ' ORDER BY ' . implode (",",$orderBy);
}

//exécution PROPRE de la requête (dans un bloc TRY/CATCH )
try {
  $stmt = $pdo->prepare($requete);
  $stmt->execute($datas);
  $resu = $stmt->fetchAll();
} catch (Exception $e) {
  echo "Erreur dans la requete : " . $requete;
  echo "<br>" . $e->getMessage();
  echo "<br> DATAS : " . print_r($datas, true);
}

//le temps des tests :
if(empty($resu)){
  echo "<br> Requete :" . $requete ;
  echo "<br>Datas :<br>";
  print_r($datas);
}

Merci mais j'ai trouvé finalement,

j'avais
if ($_GET['moisSelec'] != "all" AND $_GET['annee'] == "ALL" ){
				$requete .= ' AND MONTH(dateExpiration) = '.$_GET["moisSelec"].' ORDER BY dateExpiration ASC';
			}


			if ($_GET['moisSelec'] != "all" AND $_GET['annee'] != "ALL" ){
				$requete .= ' AND MONTH(dateExpiration) = '.$_GET["moisSelec"].' AND YEAR(dateExpiration) = '.$_GET["annee"].' ORDER BY dateExpiration ASC';
			}

			if ($_GET['moisSelec'] == "all" AND $_GET['annee'] != "ALL" ){
				$requete .= ' AND  YEAR(dateExpiration) = '.$_GET["annee"].' ORDER BY dateExpiration ASC';
			}


Mais du coup il me manquait juste :
if ($_GET['moisSelec'] == "all" AND $_GET['annee'] == "ALL" ){
				$requete .= ' AND  YEAR(dateExpiration) = '.$_GET["annee"].' ORDER BY dateExpiration ASC';
			}
Messages postés
33031
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
24 juin 2021
3 580 > antho
Sauf qu'en utilisant directement les variables $_GET dans ta requête... ton code contient une grosse faille de sécurité par injection SQL ..
Je t'invite fortement à t'inspirer du code que je t'ai donné (et des liens ) afin d'utiliser correctement les requêtes préparées..
>
Messages postés
33031
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
24 juin 2021

Ok merci je vais regarder ça alors :)
Messages postés
16136
Date d'inscription
lundi 9 juin 2008
Statut
Contributeur
Dernière intervention
24 juin 2021
869 > antho
pourras-tu marquer la discussion comme résolue?