Le WordPress d'aujourd'hui, décodé pour les développeurs

Astuces

WP_Query et meta_value_num : trier des biens immobiliers par prix sans extension

Un tri par prix qui classe 90 000 avant 100 avant 9 000 : le symptôme classique d'un tri alphabétique sur un champ numérique. Le paramètre orderby meta_value_num corrige ce défaut sans extension tierce.

Par WordPress Développement • 22 juin 2021 • 4 min de lecture • Aucun commentaire
WP_Query et meta_value_num : trier des biens immobiliers par prix sans extension

90 000 avant 100 000, mais aussi avant 9 000 : voilà ce que produisait le tri « prix croissant » d’un site vitrine pour un réseau d’agences immobilières indépendantes, avant que le développeur précédent ne me transmette le dossier. Le prix de chaque bien était stocké en champ personnalisé, trié avec orderby => 'meta_value', un paramètre qui compare les valeurs comme des chaînes de caractères plutôt que comme des nombres.

Le symptôme est trompeur : le tri fonctionne, dans le sens où il classe les biens dans un certain ordre, mais cet ordre est celui de la comparaison alphabétique d’une chaîne. « 90000 » est « plus petit » que « 100000 » alphabétiquement, car le caractère « 9 » vient après « 1 » dans la comparaison caractère par caractère, mais dès le deuxième caractère la comparaison bascule différemment selon la longueur des chaînes. Le résultat paraît aléatoire à qui ne connaît pas la cause exacte.

Le tri fautif, tel qu’il apparaissait dans le thème

Voici la requête d’origine, qui illustre parfaitement le piège : elle ne produit aucune erreur, aucun avertissement, elle retourne simplement un ordre incorrect, ce qui la rend difficile à repérer sans comparer manuellement les prix affichés.

$biens = new WP_Query( array(
    'post_type'  => 'bien',
    'meta_key'   => 'prix_bien',
    'orderby'    => 'meta_value',
    'order'      => 'ASC',
    'posts_per_page' => 20,
) );

La correction : meta_value_num

Le paramètre orderby accepte la valeur meta_value_num, qui indique explicitement à WordPress de convertir les valeurs en nombre avant de les comparer. C’est un changement d’un seul mot, mais qui suffit à corriger entièrement le classement.

$biens = new WP_Query( array(
    'post_type'  => 'bien',
    'meta_key'   => 'prix_bien',
    'orderby'    => 'meta_value_num',
    'order'      => 'ASC',
    'posts_per_page' => 20,
) );
L'essentiel à retenir : meta_value trie comme du texte, meta_value_num trie comme un nombre ; Le type de champ doit rester cohérent à l'enregistrement ; Aucune extension nécessaire pour un tri numérique correct

Pourquoi le type de champ compte autant que le paramètre orderby

Corriger le paramètre orderby ne suffit pas si le champ lui-même contient des valeurs incohérentes : un prix enregistré une fois comme 250000 et une autre fois comme 250 000 avec un espace, ou 250000€ avec le symbole monétaire, casse le tri numérique tout autant qu’un mauvais paramètre. La discipline de saisie compte autant que la requête.

add_action( 'save_post_bien', function ( $post_id ) {
    if ( isset( $_POST['prix_bien'] ) ) {
        $prix = preg_replace( '/[^0-9]/', '', $_POST['prix_bien'] );
        update_post_meta( $post_id, 'prix_bien', absint( $prix ) );
    }
} );

Cette normalisation à l’enregistrement garantit que le champ ne contiendra jamais que des nombres entiers purs, condition indispensable pour que meta_value_num fonctionne de façon fiable sur l’ensemble du catalogue.

Comparer les deux comportements sur un cas concret

Prix stockésOrdre avec meta_valueOrdre avec meta_value_num
9 000, 90 000, 100 000100 000, 9 000, 90 0009 000, 90 000, 100 000
1 200, 850, 15 0001 200, 15 000, 850850, 1 200, 15 000

Ce tableau, présenté tel quel à l’équipe du réseau d’agences, a suffi à convaincre que le problème ne venait ni du contenu des fiches ni d’un bug d’affichage, mais bien d’un choix de paramètre à corriger une fois pour toutes.

Étendre le tri numérique à d’autres champs

Une fois le principe compris, plusieurs autres champs du même site méritaient la même correction, chacun avec sa propre logique de tri :

  • La surface habitable, souvent triée par erreur comme du texte pour les mêmes raisons que le prix.
  • Le nombre de pièces, un champ court où l’erreur passe presque inaperçue tant que le catalogue reste petit, mais qui devient visible dès qu’il dépasse neuf pièces.
  • La date de disponibilité du bien, qui nécessite en revanche orderby => 'meta_value' avec un format Ymd, car un tri numérique sur une date écrite autrement produirait un résultat tout aussi faux.

Un tri qui ne renvoie jamais d’erreur mérite d’être vérifié aussi souvent qu’un tri qui plante : l’absence de message ne garantit jamais l’exactitude du résultat.

Notre verdict

Le paramètre meta_value_num de WP_Query existe depuis les premières versions de l’API des requêtes personnalisées et ne nécessite strictement aucune extension tierce. Le vrai travail consiste à garantir que les données stockées restent des nombres purs, faute de quoi même le bon paramètre de tri ne produira pas le résultat attendu. Ce dossier ne traite volontairement pas la pagination du listing, qui repose sur une logique distincte, à combiner avec ce tri une fois celui-ci corrigé.

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *

Partager :

À propos de l'auteur

WordPress Développement

Développeur WordPress, passionné par Elementor, le FSE et l’automatisation par IA.

Voir tous ses articles

Dans la même veine

À lire aussi