2 critères sur un ORDER BY

Répondre


Cette question est un moyen d’empêcher des soumissions automatisées de formulaires par des robots.
Smileys
:D :) :( :o :shock: :? 8-) :lol: :x :P :oops: :cry: :evil: :twisted: :roll: :wink: :!: :?: :idea: :arrow: :| :mrgreen: =D> #-o =P~ :^o :non: :priere: 8-|
Voir plus de smileys
  Revue du sujet
 

  Étendre la vue Revue du sujet : 2 critères sur un ORDER BY

Re: 2 critères sur un ORDER BY

par yann18 » 03 août 2016, 12:00

ton code fonctionnait-il avant que tu n'ajoutes les critères de tri?
quelles erreurs rencontres-tu?
affiche la requête.

Re: 2 critères sur un ORDER BY

par blinz » 01 août 2016, 21:18

Sinon j'essai ceci pourtant simple je pense afficher les coup de coeur par odre croissant du plus récent au plus vieux en gros
en rajoutant BY id_loisirs mais ça ne marche pas.
Je m'embrouille grave la
// Ordre d'affichage 
		if (!empty($_REQUEST['ville'])) {
		$sql .= " ORDER BY id_loisirs, CASE
		WHEN heart = 1 THEN 3
		WHEN id_simply_user != 999 THEN 2
		WHEN id_simply_user = 999 THEN 1
		END DESC 
		LIMIT ".intval(($page-1)*$parPage).", ".$parPage;

Re: 2 critères sur un ORDER BY

par blinz » 01 août 2016, 20:37

Salut,
Alors ç'est ce que je cherche à faire "presque".
la requete marche bien dans PMA mais dans mon script je dois louper un truc.
Mon code est tel quel actuellement:
$sql = 'SELECT * FROM loisirs JOIN `regions` ON `regions`.`region_id` = `loisirs`.`id_region` WHERE  loisirs.date_fin_sortie > NOW() AND loisirs.valide = 1';
  // region
  if(!empty($_REQUEST['region'])){
    // FIXME : sql injectin spoted
    $sql .= ' AND regions.url = \''.$_REQUEST['region'].'\'' ;
  }
  if(!empty($_REQUEST['departement'])){
    $sql .=  ' AND loisirs.id_departements = '.$_REQUEST['departement'];
  }
  
  if(!empty($_REQUEST['loisir']) ){
    // FIXME : sql injectin spoted
    $sql .=  ' AND loisirs.genre_loisir = \''.$_REQUEST['loisir'].'\'' ; // loisir
  }
  

  // FIXME : sql injectin spoted
  if(!empty($du) && !empty($au)) {
    $sql .= ' AND (DATE_FORMAT(loisirs.date_debut_sortie, \'%Y-%m-%d\') <= \''.$du.'\' AND DATE_FORMAT(loisirs.date_fin_sortie, \'%Y-%m-%d\') >= \''.$au.'\')';
  }
  
   // Recherche par ville
  if(!empty($_REQUEST['ville'])) {
    $sql .= ' AND loisirs.city = \''. getRealValue($_REQUEST['ville']). '\'';
  }



	$req = $bdd->query($sql);

	// on affiche le nombre de sorties en fonction des filtres       
	$nb = $req->rowCount();
	if ($req->fetchColumn() > 0) {
		
	// on affiche le h1 en fonction de la region 
	$region_id = !empty($_REQUEST['region']) ? regionByUrl($_REQUEST['region']) : NULL; 
	$region_id = !empty($_SESSION['membre']['id_region']) && empty($_REQUEST['region']) ? $_SESSION['membre']['id_region'] : $region_id; 
	$h1 = $nb;
		
	// Par ville	
	$h1 .= empty($_REQUEST['ville']) && empty($_REQUEST['departement']) && empty($_REQUEST['loisir']) && empty($_REQUEST['region']) ? ' <h1 class="page-heading"> annonces pour trouver une idée de sortie !</h1>' : NULL; // La ville
	$h1 .= !empty($_REQUEST['ville']) && empty($_REQUEST['departement']) && empty($_REQUEST['loisir']) && !empty($_REQUEST['region'])? ' <h1 class="page-heading"> annonces pour sortir à '. ucfirst($_REQUEST['ville']).'</h1>' : NULL; // La ville
	$h1 .= !empty($_REQUEST['ville']) && !empty($_REQUEST['loisir']) && empty($_REQUEST['departement']) ? '<h1 class="page-heading"> sorties pour '.ucfirst($_REQUEST['loisir']).' à '. ucfirst ($_REQUEST['ville']).' </h1>' : NULL; // La ville
	$h1 .= !empty($region_id) && empty($_REQUEST['departement']) && empty($_REQUEST['loisir']) && empty($_REQUEST['ville']) ? '<h1 class="page-heading"> sorties pour sortir en ' .$aRegion[$region_id] .'</h1>': NULL; // La région
	$h1 .= !empty($_REQUEST['loisir']) &&  empty($_REQUEST['departement']) &&  !empty($_REQUEST['region'])  &&  empty($_REQUEST['ville']) ? ' <h1 class="page-heading"> sorties ' .strtolower($_REQUEST['loisir']).' en ' .$aRegion[$region_id] .' </h1>': NULL; // Le type de sortie

	// Département
	$h1 .= !empty($_REQUEST['departement']) &&  !empty($_REQUEST['loisir']) ? '<h1 class="page-heading"> des sorties ' .ucfirst($_REQUEST['loisir']).' en '.$depts[$_REQUEST['departement']].' ('.$_REQUEST['departement'].')</a></h1>' : NULL; // Le département
	$h1 .= !empty($_REQUEST['departement']) &&  !empty($_REQUEST['region']) &&  empty($_REQUEST['loisir']) &&  empty($_REQUEST['ville'])   ? '<h1 class="page-heading"> sortir en '.$depts[$_REQUEST['departement']].' ('.$_REQUEST['departement'].')</h1>' : NULL; // Le département
		
	// Affichage de la date en fr du datepicker 
	$h1 .= !empty($du) ? "  le <strong>" .date('d/m/Y', strtotime($du))."</strong>" : NULL; // La date choisis selon les filtres
	echo '<div class="col-md-12 result-search"><div class="col-md-5 pad-15"> '.$h1.'</div>'?>
    <form  method="POST">
    <div class="col-md-3 col-sm-3 max">  
    <div class="input-group">
    <input class="search-motor form-control"  title="Recherche de sortie par date "id="datetimepicker2" name="datetimepicker" placeholder="Recherche par date" type="text" readonly value="<?php echo !empty($_REQUEST['datetimepicker']) ? $_REQUEST['datetimepicker'] : NULL; ?>">
    <span class="input-group-addon custom">
    <button class="btn btn-default search-btn" type="submit"><i class="fa fa-calendar-o"></i></button>
    </span>
    </div>
    </div>
    </form>
	<div class="col-md-4 col-sm-12 max">
    <form id="choice" method="POST" action="">
    <div class="input-group">
    <input title="Recherche par ville" placeholder="Recherche par ville" class="search-motor form-control"  value="<?php echo  !empty($_REQUEST['ville']) ? $_REQUEST['ville'] : NULL;?>" name="ville" id="ville" type="search">
    <span class="input-group-btn">
    <button name="submit_city" id="submit_city" type="submit" class="btn btn-default search-btn">GO !</button>
    </span>
    </div>
    </form>
    </div> 
    </div>     
    <article class="col-main"> 
    <?php include("include/optimisation.php"); ?>  
      
    <?php echo '<div class="category-products">
    <ol class="products-list" id="products-list">'."\n";	
	}
		// Si il n y a que la région de demandée
		if (!empty($_REQUEST['region']) && empty($_REQUEST['loisir']) && empty($_REQUEST['departement'])  && empty($_REQUEST['ville'])){
		$valeur_paginate =  'region-'.$_REQUEST['region'];
		}
		
		// Si il y a une région de demandée et un loisir
		else if (!empty($_REQUEST['loisir']) && !empty($_REQUEST['loisir']) && empty($_REQUEST['departement']))  {
		$valeur_paginate =  'activite-'.$_REQUEST['loisir'];
		}
		
		// Si il y a une région de demandée et un loisir
		else if (!empty($_REQUEST['region']) && !empty($_REQUEST['departement']) && empty($_REQUEST['loisir'])) {
		$valeur_paginate =  'sorties-du-'.$_REQUEST['departement'];
		}
		
		// Si il y a une région de demandée et un loisir
		else if (!empty($_REQUEST['region']) && !empty($_REQUEST['departement']) && !empty($_REQUEST['loisir'])) {
		$valeur_paginate = 'sorties-du-'.$_REQUEST['departement'];
		}
		
		// Si il y a une région de demandée et un loisir
		else if (!empty($_REQUEST['region'])  && !empty($_REQUEST['loisir']) && !empty($_REQUEST['ville'])) {
		$valeur_paginate = 'sorties-du-'.$_REQUEST['departement'];
		}
		
		// Si il y a une région de demandée et un loisir
		else if (!empty($_REQUEST['region'])  && !empty($_REQUEST['ville'])) {
		$valeur_paginate = 'ville-de-'.simplification($_REQUEST['ville']);	
		}	
		?>
		<?php
		$nbre_annonces_par_page = 15;
		$nbre_pages_max_gauche_et_droite = 4;
		$last_page = ceil($nb / $nbre_annonces_par_page);
		if(isset($_GET['page']) && is_numeric($_GET['page'])){
		$page_num = $_GET['page'];
		} else {
		$page_num = 1;
		}
		if($page_num < 1){
		$page_num = 1;
		} else if($page_num > $last_page) {
		$page_num = $last_page;
		}
		$limit = 'LIMIT '.($page_num - 1) * $nbre_annonces_par_page. ',' . $nbre_annonces_par_page;
		$pagination = '';
		if($last_page != 1){
		if($page_num > 1){
		$previous = $page_num - 1;
		$pagination .= '<a href="'.$valeur_paginate.($previous > 1 ? '-page-'.$previous : null).'.html" class="page" data-page="'.$previous.'" data-du="'.$du.'" data-au="'.$au.'"><i class="fa fa-angle-left"></i></a> &nbsp; &nbsp;';
		for($i = $page_num - $nbre_pages_max_gauche_et_droite; $i < $page_num; $i++){
		if($i > 0){
		$pagination .= '<a href="'.$valeur_paginate.($i > 1 ? '-page-'.$i : null).'.html" class="page" data-page="'.$i.'" data-du="'.$du.'" data-au="'.$au.'">'.$i.'</a> &nbsp;';
		}
		}
		}
		$pagination .= '<span class="active">'.$page_num.'</span>&nbsp;';
		for($i = $page_num+1; $i <= $last_page; $i++){	
		$pagination .= '<a href="'.$valeur_paginate.'-page-'.$i.'.html" class="page" data-page="'.$i.'" data-du="'.$du.'" data-au="'.$au.'">'.$i.'</a> ';
		if($i >= $page_num + $nbre_pages_max_gauche_et_droite){
		break;
		}
		}
		if($page_num != $last_page){
		$next = $page_num + 1;
		$pagination .= '<a href="'.$valeur_paginate.'-page-'.$next.'.html" class="page" data-page="'.$next.'" data-du="'.$du.'" data-au="'.$au.'"><i class="fa fa-angle-right"></i></a> ';
		}
		}
	
		// Ordre d'affichage 
		$sql .= " ORDER BY CASE
		WHEN heart = 1 THEN 3
		WHEN id_simply_user != 999 THEN 2
		WHEN id_simply_user = 999 THEN 1
		END DESC 
		LIMIT ".intval(($page-1)*$parPage).", ".$parPage; 
		
		$req = $bdd->query($sql);	
		$nb2 = $req->rowCount();
Je veut bien l'accorder on peut certainement améliorer mon code :p

Re: 2 critères sur un ORDER BY

par yann18 » 01 août 2016, 15:59

Pour inclure la requête précédente dans ton script:
$sql = 'SELECT * FROM loisirs JOIN `regions` ON `regions`.`region_id` = `loisirs`.`id_region` WHERE  loisirs.date_fin_sortie > NOW() AND loisirs.valide = 1
AND loisirs.id_type_loisirs IN (SELECT MAX(id_type_loisirs) AS max_id FROM loisirs GROUP BY id_type_loisirs )
';
sachant que la partie dynamique(choix ville, choix région...) de ta requête reste inchangée.

Re: 2 critères sur un ORDER BY

par yann18 » 01 août 2016, 15:52

ta requête est syntaxiquement incorrecte car tu ne fais qu'enchaîner des SELECT sans condition ni jointure.Voilà comment tu peux récupérer les derniers loisirs en fonction d'une région, d'une ville...
SELECT * FROM loisirs JOIN `regions` ON `regions`.`region_id` = `loisirs`.`id_region` 
WHERE loisirs.date_fin_sortie > NOW() AND loisirs.valide = 1
AND loisirs.id_type_loisirs IN (SELECT MAX(id_type_loisirs) AS max_id FROM loisirs GROUP BY id_type_loisirs )
AND regions.url = 'rhone-alpes' AND loisirs.city = 'Grenoble'
ORDER BY CASE WHEN heart = 1 THEN 3
WHEN id_simply_user != 999 THEN 2
WHEN id_simply_user = 999 THEN 1
END DESC
3/ Les annonces de id_usuer 999 mais en les affichant par type de loisirs
j'entends par là les annonces du 999 doivent être ordonnées par type de loisirs? si c'est le cas , il n'est probablement pas possible de le faire en sql mais c'est faisable en php.
Essaies déjà de tester la requête sans pourtant tenir compte du tri des annonces du 999.Après le teste je pourrai de t'expliquer comment le faire en php

Re: 2 critères sur un ORDER BY

par blinz » 31 juil. 2016, 11:06

Ca se complique quand même, pour rappel le but final et d'établir un ordre par defaut
1/ on affiche les annonce heart
2/ Les annonces différentes de id_usuer 999
3/ Les annonces de id_usuer 999 mais en les affichant par type de loisirs

En testant la requête je me retrouve avec une erreur:
Requete:
$sql = ' SELECT * FROM loisirs lo JOIN
                      ( 
                             SELECT MAX(id_type_loisirs) AS max_id, id_type_loisirs FROM loisirs GROUP BY id_type_loisirs 
                        ) req
                        ON lo.id_type_loisirs = req.max_id
                     
ORDER BY CASE
          WHEN heart = 1 THEN 3
          WHEN id_simply_user != 999 THEN 2
          WHEN id_simply_user = 999 THEN 1
          END DESC 
   	  LIMIT '.intval(($page-1)*$parPage).", ".$parPage;
Erreur:
Warning: PDO::query(): SQLSTATE[42000]: Syntax error or access violation: 1064 You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near 'SELECT * FROM loisirs lo JOIN ( ' at line 1 in /home/www/lasortie/list.php on line 326

Fatal error: Call to a member function rowCount() on a non-object in /home/www/lasortie/list.php on line 327


Les lignes en question sont: ( 326 et ligne 327 )
$req = $bdd->query($sql);	
		$nb2 = $req->rowCount();
		if($nb2 > 0) {
Merci à vous ;)
PS, la requete executive nous donne :
SELECT * FROM loisirs JOIN `regions` ON `regions`.`region_id` = `loisirs`.`id_region` WHERE loisirs.date_fin_sortie > NOW() AND loisirs.valide = 1
AND regions.url = 'rhone-alpes' AND loisirs.city = 'Grenoble'
SELECT * FROM loisirs lo JOIN ( SELECT MAX(id_type_loisirs) AS max_id, id_type_loisirs FROM loisirs GROUP BY id_type_loisirs ) req ON lo.id_type_loisirs = req.max_id
ORDER BY CASE WHEN heart = 1 THEN 3
WHEN id_simply_user != 999 THEN 2
WHEN id_simply_user = 999 THEN 1
END DESC
J'ai testé mais sains succés :
// Ordre d'affichage 
		$sql .= " ORDER BY CASE
		WHEN heart = 1 THEN 3
		WHEN id_simply_user != 999 THEN 2
		WHEN id_simply_user = 999 GROUP BY id_type_loisirs THEN 3 
		END DESC 
		LIMIT ".intval(($page-1)*$parPage).", ".$parPage;
Le problème est que par rapport à mon code je dois commencer par :
// Ordre d'affichage
$sql .= " ORDER BY....

Re: 2 critères sur un ORDER BY

par moogli » 27 juil. 2016, 09:08

c'est la définition d'un alias pour le nom de la table : from loisir lo
il est aussi possible d'utiliser le mot clef as pour lever l’ambiguïté de la chose : from loisir as lo

dans le cas de ta requête cela permet de ne pas confondre les tables (vue que le subselect dans le join porte sur la même table)

@+

Re: 2 critères sur un ORDER BY

par blinz » 26 juil. 2016, 20:03

Alors excuse moi mais la requete se complique pas mal quand même:
Ca donnerai ça ?
$sql = ' SELECT * FROM loisirs lo JOIN
                      ( 
                             SELECT MAX(id_type_loisirs) AS max_id, id_type_loisirs FROM loisirs GROUP BY id_type_loisirs 
                        ) req
                        ON lo.id_type_loisirs = req.max_id
                     
ORDER BY CASE
          WHEN heart = 1 THEN 3
          WHEN id_simply_user != 999 THEN 2
          WHEN id_simply_user = 999 THEN 1
          END DESC 
	 	  LIMIT '.intval(($page-1)*$parPage).", ".$parPage;
Que veut dire lo dans lo JOIN

Merci encore

Re: [RESOLU] 2 critères sur un ORDER BY

par yann18 » 26 juil. 2016, 17:19

mais si je souhaite classé les annonces de l'utilisateur 999 par id_type loisir dois je faire ceci:
$sql .= " ORDER BY CASE
          WHEN heart = 1 THEN 3
          WHEN id_simply_user != 999 THEN 2
          WHEN id_simply_user = 999 ORDER by id_type_loisirs THEN 1
          END DESC 
	 LIMIT ".intval(($page-1)*$parPage).", ".$parPage;
Merci encore
d'ordinaire quand il ya différents tris à faire on laisse à l'utilisateur de l'application l'exclusivité d'agir sur un lien(ou bouton) devant déclencher un ordre sql qui exécute un critère précis de tri.
Après pour ce que tu souhaites, il est possible de fusionner (avec UNION) les requêtes. chacune des requêtes impliquées dans la fusion doit définir son propre critère de tri.

Il est également possible de le faire en php, en stockant toutes les lignes issues de la requête dans un tableau(t1) php et les lignes spécifiques à l'utilisateur 999 dans un autre tableau(t2) qui doit être trié la fin de la boucle. Dès lors tu peux boucler sur t1 pour afficher des données.Bien sûr qu'avant d'afficher il faut vérifier que t'as bien à faire au user 999 si c'est le cas boucler sur t1

Re: 2 critères sur un ORDER BY

par yann18 » 26 juil. 2016, 16:57

Pour afficher le dernier loisir selon le type loisir, on peut joindre la table des loisirs aux résultats d'une requête qui extrait le l'id maxi du type loisir:
$sql = ' SELECT * FROM loisirs lo JOIN
                      ( 
                             SELECT MAX(id_type_loisirs) AS max_id, id_type_loisirs FROM loisirs GROUP BY id_type_loisirs 
                        ) req
                        ON lo.id_type_loisirs = req.max_id
                     
ORDER BY ...'

Re: 2 critères sur un ORDER BY

par blinz » 25 juil. 2016, 23:09

Re, Alors après différents test je n'arrive toujours pas à afficher selon les id_type_loisirs.
Le but étant d'afficher le derniere loisirs rajouté en bdd pour chaque type de loisirs.
Dans l'idée :
GROUP BY id_type_loisirs ORDER BY loisirs.id_loisirs DESC

J'ai essayer ceci:
$sql .= " ORDER BY CASE
          WHEN heart = 1 THEN 3
          WHEN id_simply_user != 999 THEN 2
          WHEN id_simply_user = 999 ORDER by id_type_loisirs THEN 1
          END DESC 
   LIMIT ".intval(($page-1)*$parPage).", ".$parPage;
Merci encore

Re: [RESOLU] 2 critères sur un ORDER BY

par blinz » 20 juil. 2016, 22:48

Juste une dernière question mon code marche maintenant.
$sql .= " ORDER BY CASE
          WHEN heart = 1 THEN 3
          WHEN id_simply_user != 999 THEN 2
          WHEN id_simply_user = 999 THEN 1
          END DESC 
	 LIMIT ".intval(($page-1)*$parPage).", ".$parPage;
mais si je souhaite classé les annonces de l'utilisateur 999 par id_type loisir dois je faire ceci:
$sql .= " ORDER BY CASE
          WHEN heart = 1 THEN 3
          WHEN id_simply_user != 999 THEN 2
          WHEN id_simply_user = 999 ORDER by id_type_loisirs THEN 1
          END DESC 
	 LIMIT ".intval(($page-1)*$parPage).", ".$parPage;
Merci encore

Re: 2 critères sur un ORDER BY

par blinz » 19 juil. 2016, 21:07

Bon
J'ai trouver fallait juste modifier cette ligne:
WHEN heart IS NOT NULL THEN 3
par
WHEN heart = 1 THEN 3

Re: 2 critères sur un ORDER BY

par blinz » 19 juil. 2016, 20:58

C'est fou !!!
J'ai tester ton code c'est vrai ça marche le résultat attendu et exactement celui que je souhaite.
Mais de mon coté problème.
J'ai donc fait un echo de $sql pour voir ce qu'elle à dans le ventre et voilà :
SELECT * FROM loisirs JOIN `regions` ON `regions`.`region_id` = `loisirs`.`id_region` WHERE loisirs.date_fin_sortie > NOW() AND loisirs.valide = 1 AND regions.url = 'rhone-alpes' ORDER BY CASE WHEN heart IS NOT NULL THEN 3 WHEN id_simply_user != 999 THEN 2 WHEN id_simply_user = 999 THEN 1 END DESC LIMIT 0, 15
Un peu long quand même, voici toutes les requetes de la page:
$sql = 'SELECT * FROM loisirs JOIN `regions` ON `regions`.`region_id` = `loisirs`.`id_region` WHERE  loisirs.date_fin_sortie > NOW() AND loisirs.valide = 1';
	// region
	if(!empty($_REQUEST['region'])){
	  // FIXME : sql injectin spoted
	  $sql .= ' AND regions.url = \''.$_REQUEST['region'].'\'' ;
	}
	if(!empty($_REQUEST['departement'])){
	  $sql .=  ' AND loisirs.id_departements = '.$_REQUEST['departement'];
	}
	
	if(!empty($_REQUEST['loisir']) ){
	  // FIXME : sql injectin spoted
	  $sql .=  ' AND loisirs.genre_loisir = \''.$_REQUEST['loisir'].'\'' ; // loisir
	}
	
	// Recherche par date
	// FIXME : $du et $au n'existe pas ici ;)
	// FIXME : sql injectin spoted
	if(!empty($du) && !empty($au)) {
	  $sql .= ' AND (DATE_FORMAT(loisirs.date_debut_sortie, \'%Y-%m-%d\') <= \''.$du.'\' AND DATE_FORMAT(loisirs.date_fin_sortie, \'%Y-%m-%d\') >= \''.$au.'\')';
	}
	
	 // Recherche par ville
	if(!empty($_REQUEST['ville'])) {
	  $sql .= ' AND loisirs.city = \''. getRealValue($_REQUEST['ville']). '\'';
	}
	
	// Recherche par salle
	if(!empty($_REQUEST['manufacturer'])){
	  $sql .= ' AND loisirs.manufacturer = \''. getRealValue($_REQUEST['manufacturer'] , 'manufacturer') .'\'';
	}

$sql .= " ORDER BY CASE
          WHEN heart IS NOT NULL THEN 3
          WHEN id_simply_user != 999 THEN 2
          WHEN id_simply_user = 999 THEN 1
          END DESC 
	 LIMIT ".intval(($page-1)*$parPage).", ".$parPage;
	 
	 echo $sql;
Pour le coup en bdd j'ai l'id_user ( 435 ) qui à une annonce en heart et pourtant je ne la vois pas....
Un truc de DINGUE !!!

Re: 2 critères sur un ORDER BY

par yann18 » 19 juil. 2016, 20:11

Le résultat attendu est assez étrange car la premiere est bien un différent de 999 mais après que des 999 et le heart disparu ....
tout dépend des données contenues dans tes tables.A priori toutes les annonces coup de coeur ont toutes été postées par l'utilisateur 999 ce qui expliquerait la disparition de ces annonces.

L'exemple suivant affichera en priorité tous les fruits dont le heart est 1 suivis de tous les fruits du user 999
CREATE TABLE fruit
(
id int auto_increment NOT NULL,
nom varchar(255) NOT NULL,
heart boolean DEFAULT 0,
user int(8),
PRIMARY KEY (id)
);

INSERT fruit VALUES(null,'abricot', 1, 800),
(null,'fraise', 1, 800),
(null,'pomme', 1, 801),
(null,'kiwi', 0, 999),
(null,'pêche', 0, 999),
(null,'orange', 0, 800),
(null,'poire', 1, 8001),
(null,'cerise', 1, 8001);
mysql> select * from  fruit order by case 
when heart = 1 then 3 
when user = 999 then 2 end desc;
+----+---------+-------+------+
| id | nom     | heart | user |
+----+---------+-------+------+
|  1 | abricot |     1 |  800 |
|  2 | fraise  |     1 |  800 |
|  3 | pomme   |     1 |  801 |
|  7 | poire   |     1 | 8001 |
|  8 | cerise  |     1 | 8001 |
|  4 | kiwi    |     0 |  999 |
|  5 | pêche   |     0 |  999 |
|  6 | orange  |     0 |  800 |
+----+---------+-------+------+