(ORDER BY) impossible de trier une liste avec un ORDER BY

Résolu/Fermé
antho - 26 févr. 2021 à 15:44
yg_be
Messages postés
20031
Date d'inscription
lundi 9 juin 2008
Statut
Contributeur
Dernière intervention
12 août 2022
- 2 mars 2021 à 12:28
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

jordane45
Messages postés
36047
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
12 août 2022
4 275
26 févr. 2021 à 16:26
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://forums.commentcamarche.net/forum/affich-37584941-php-pdo-gerer-les-erreurs

Ainsi que ça
https://forums.commentcamarche.net/forum/affich-37584947-php-gestion-des-erreurs-debogage-et-ecriture-du-code
0
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 :/
0
yg_be
Messages postés
20031
Date d'inscription
lundi 9 juin 2008
Statut
Contributeur
Dernière intervention
12 août 2022
1 185
1 mars 2021 à 11:03
bonjour, quel résultat obtiens-tu quand "ORDER BY ne fonctionne pas"?
0
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.
0
yg_be
Messages postés
20031
Date d'inscription
lundi 9 juin 2008
Statut
Contributeur
Dernière intervention
12 août 2022
1 185
1 mars 2021 à 11:26
cela fonctionne-t-il différemment si tu retires la clause ORDER BY?
0
yg_be
Messages postés
20031
Date d'inscription
lundi 9 juin 2008
Statut
Contributeur
Dernière intervention
12 août 2022
1 185 > yg_be
Messages postés
20031
Date d'inscription
lundi 9 juin 2008
Statut
Contributeur
Dernière intervention
12 août 2022

1 mars 2021 à 11:29
montre-nous ce que contient ta variable $requete pour chacun des cas, ainsi que le résultat obtenu.
0
antho > yg_be
Messages postés
20031
Date d'inscription
lundi 9 juin 2008
Statut
Contributeur
Dernière intervention
12 août 2022

1 mars 2021 à 12:44
Voici ma requête :
$requete = 'SELECT * from licenceseset WHERE 1=1';


Voici ce qui me permet de faire une recherche par nom de produit mais sans le tri avec le ORDER BY
			if (isset($_GET['nomProduit']) AND $_GET['nomProduit']!="tous"){
				$requete .= ' AND nomProduit LIKE"%'.$_GET['nomProduit'].'%"';
			}

Sans le ORDER BY, toutes mes recherches fonctionnent sauf que quand je fais une recherche par nom de produit, ce dernier ne se trie pas.

Voici ce qui me permet de faire ma recherche par mois et par année, trié par les ORDER BY
			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';
			}

Quand je fais une recherche par mois ou année sans spécifié le nom de produit, toue ma recherche est bien trié grace aux ORDER BY.

Mais quand je rajoute le ORDER BY à la fin de ma requête pour le nom de produit, dès que je fais une recherche avec une année ou avec un mois spécifié j'ai un message avec écrit "aucune licence ne correspond à ce résultat" alors que si j'enlève ce ORDER BY problématique, mes recherches fonctionnent mais le trie ne se fait pas :/
0
jordane45
Messages postés
36047
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
12 août 2022
4 275 > antho
1 mars 2021 à 14:52
Comme je te l'ai déjà demandé .. ce n'est pas le code php qu'on veut voir ... mais le résultat d'un ECHO de ta variable $requete afin de voir ce que contient exactement ta requête quand tu essaies de l'utiliser depuis ton code....
0
antho > jordane45
Messages postés
36047
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
12 août 2022

1 mars 2021 à 15:00
Quand je fais un echo de ma requête, je ressort
'SELECT * from licenceseset WHERE 1=1'
sur mon site
0
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 :/
0
jordane45
Messages postés
36047
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
12 août 2022
4 275
1 mars 2021 à 12:21
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
0

Vous n’avez pas trouvé la réponse que vous recherchez ?

Posez votre question
jordane45
Messages postés
36047
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
12 août 2022
4 275
1 mars 2021 à 16:13
<?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);
}


0
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 :/
0
jordane45
Messages postés
36047
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
12 août 2022
4 275 > antho
1 mars 2021 à 20:45
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...
0
jordane45
Messages postés
36047
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
12 août 2022
4 275
1 mars 2021 à 20:59
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);
}

0
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';
			}
0
jordane45
Messages postés
36047
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
12 août 2022
4 275 > antho
2 mars 2021 à 11:15
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..
0
antho > jordane45
Messages postés
36047
Date d'inscription
mercredi 22 octobre 2003
Statut
Modérateur
Dernière intervention
12 août 2022

2 mars 2021 à 11:15
Ok merci je vais regarder ça alors :)
0
yg_be
Messages postés
20031
Date d'inscription
lundi 9 juin 2008
Statut
Contributeur
Dernière intervention
12 août 2022
1 185 > antho
2 mars 2021 à 12:28
pourras-tu marquer la discussion comme résolue?
0