« Le moteur de recherche natif de PrestaShop est limité » est une phrase qu’on lit partout, et elle est vraie. Mais elle est presque toujours justifiée par de mauvaises raisons, ce qui conduit des marchands à payer un moteur externe alors qu’un réindexage aurait suffi, et d’autres à s’en priver alors qu’ils en ont réellement besoin.
Voici ce que fait le moteur natif, lu dans le cœur de PrestaShop 9.0.0. Vous y trouverez quatre limites réelles, dont une qui se dégrade silencieusement à mesure que votre catalogue grandit, ce qui est particulièrement pervers puisque le problème apparaît précisément quand les enjeux augmentent. Puis ce qui se corrige sans rien changer, et à partir de quand un moteur dédié se justifie.
Au programme :
- Comment la recherche native fonctionne réellement, tables à l’appui
- Le produit actif, en stock, et introuvable par la recherche
- La tolérance aux fautes qui cesse de fonctionner sur les gros catalogues
- Ce qui se règle gratuitement avant d’envisager autre chose
- Le seuil à partir duquel un moteur dédié devient rentable
Comment le moteur natif fonctionne réellement
PrestaShop ne cherche pas dans vos fiches produits. Il cherche dans un index de mots, construit à l’avance, réparti sur deux tables :
CREATE TABLE `ps_search_word` (
`id_word` int(10) unsigned NOT NULL auto_increment,
`id_shop` int(11) unsigned NOT NULL DEFAULT 1,
`id_lang` int(10) unsigned NOT NULL,
`word` varchar(30) NOT NULL,
PRIMARY KEY (`id_word`),
UNIQUE KEY `id_lang` (`id_lang`, `id_shop`, `word`)
);
CREATE TABLE `ps_search_index` (
`id_product` int(11) unsigned NOT NULL,
`id_word` int(11) unsigned NOT NULL,
`weight` smallint(4) unsigned NOT NULL DEFAULT 1,
PRIMARY KEY (`id_word`, `id_product`),
KEY `id_product` (`id_product`, `weight`)
);
Chaque mot du catalogue devient une ligne, associée aux produits qui le contiennent avec un poids. Ce poids dépend de l’endroit où le mot apparaît, et il est configurable : nom du produit, référence, description courte, description longue ont chacun leur pondération.
La requête de recherche ressemble alors à ceci :
SELECT DISTINCT si.id_product
FROM ps_search_word sw
LEFT JOIN ps_search_index si ON sw.id_word = si.id_word
LEFT JOIN ps_product_shop product_shop ON product_shop.id_product = si.id_product
WHERE sw.id_lang = 1
AND sw.id_shop = 1
AND product_shop.active = 1
AND product_shop.visibility IN ("both", "search")
AND product_shop.indexed = 1
AND sw.word LIKE '%chaussure%'
Tout est dans cette requête. Examinons ses quatre conséquences.
Limite 1 : le produit actif et introuvable
Regardez la condition product_shop.indexed = 1. Un produit dont le drapeau d’indexation est à zéro n’apparaîtra jamais dans les résultats de recherche, quelle que soit la requête.
Le produit existe, il est actif, il est visible en catégorie, on peut l’acheter par son URL directe. Il est simplement absent de la recherche. Aucune erreur, aucun avertissement, rien dans les journaux.
C’est le cas le plus fréquent de « la recherche de mon site ne marche pas », et il se produit typiquement après un import de catalogue, une modification en base, ou une opération de masse qui n’a pas déclenché la réindexation. La vérification tient en une requête :
SELECT COUNT(*) AS produits_non_indexes
FROM ps_product_shop
WHERE active = 1
AND visibility IN ('both', 'search')
AND indexed = 0;
Un résultat non nul, et vous avez trouvé votre problème avant d’avoir dépensé un euro. La réindexation se relance depuis le back-office, dans les paramètres de recherche.
Limite 2 : un LIKE qui ne peut pas utiliser d’index
La comparaison est sw.word LIKE '%chaussure%', avec un caractère générique en début de motif. C’est une règle de base des bases de données relationnelles : un motif commençant par un joker interdit l’usage de l’index sur la colonne. MySQL doit donc parcourir la table de mots.
Sur un catalogue de quelques milliers de références, personne ne le remarque. Sur un catalogue important, en plusieurs langues et plusieurs boutiques, la table de mots grossit dans les deux dimensions, et le coût de chaque recherche augmente avec elle.
Limite 3 : trente caractères
La colonne est déclarée varchar(30). Au-delà, un mot ne rentre pas dans l’index tel quel. Sur un catalogue grand public, c’est sans effet. Sur un catalogue technique où les références produits sont longues, c’est une part du catalogue qui devient difficile à trouver par sa référence exacte.
Dans la même famille, le réglage PS_SEARCH_MINWORDLEN écarte purement et simplement les mots plus courts que le seuil configuré. Une recherche portant sur une référence de deux ou trois caractères ne renvoie donc rien, non pas parce que le produit n’existe pas, mais parce que le terme a été jeté avant même la requête.
Limite 4 : la tolérance aux fautes qui s’éteint quand le catalogue grandit
C’est la plus intéressante, parce qu’elle contredit ce qu’on lit habituellement. PrestaShop a bien une recherche approximative, pilotée par PS_SEARCH_FUZZY, et elle s’appuie sur une distance de Levenshtein. L’affirmation « le natif ne tolère aucune faute de frappe » est donc fausse.
Mais deux réserves changent tout.
D’abord, ce n’est pas un critère de pertinence, c’est un repli. Le code lance la recherche exacte, et n’active la comparaison approximative que si elle ne renvoie rien, dans une boucle bornée par PS_SEARCH_FUZZY_MAX_LOOP. Une requête qui renvoie trois résultats médiocres ne déclenchera jamais le rattrapage.
Ensuite, et c’est le point capital, le cœur le documente lui-même :
/* If the ps_search_word table size is superior to PS_SEARCH_MAX_WORDS_IN_TABLE,
* that mean that the DB is really huge.
* To reduce the server load, we are looking only for words with same length
* that the query word.
*/
Au-delà d’un certain volume de mots indexés, la recherche approximative ne compare plus que des mots de longueur identique, pour ménager le serveur. Or une faute de frappe change très souvent la longueur du mot : une lettre oubliée, une lettre doublée. « chausure » et « chaussure » n’ont pas la même longueur, donc ne seront plus rapprochés.
Autrement dit, la tolérance aux fautes fonctionne sur une boutique de démonstration et cesse de fonctionner sur une vraie boutique, sans que rien ne le signale et sans qu’aucun réglage n’ait changé. C’est un compromis défendable du point de vue de la charge serveur, et c’est une très mauvaise nouvelle du point de vue commercial.
Ce qui se règle sans changer de moteur
Avant d’envisager une solution externe, quatre choses se corrigent gratuitement, et elles suffisent à une majorité de boutiques.
Réindexer. C’est le premier geste, et il résout à lui seul l’essentiel des cas signalés. À automatiser après tout import, au même titre que les autres contrôles sur la donnée catalogue.
Ajuster PS_SEARCH_MINWORDLEN. La valeur par défaut est pensée pour du langage naturel. Si vos clients cherchent par référence courte, elle vous dessert.
Revoir les pondérations. Nom, référence, description courte et description longue ont des poids distincts, et vous pouvez lire les vôtres directement :
SELECT name, value
FROM ps_configuration
WHERE name LIKE 'PS_SEARCH_WEIGHT_%'
OR name IN ('PS_SEARCH_MINWORDLEN', 'PS_SEARCH_FUZZY', 'PS_SEARCH_FUZZY_MAX_LOOP')
ORDER BY name;
Sur un catalogue où les clients cherchent par référence, remonter PS_SEARCH_WEIGHT_REF au-dessus du poids du nom change les résultats immédiatement, sans rien installer. C’est le réglage le plus rentable et le moins souvent touché.
Utiliser les alias. PrestaShop dispose nativement d’une table de correspondance, contrairement à ce qu’on lit souvent :
CREATE TABLE `ps_alias` (
`id_alias` int(10) unsigned NOT NULL auto_increment,
`alias` varchar(191) NOT NULL,
`search` varchar(255) NOT NULL,
`active` tinyint(1) NOT NULL DEFAULT '1',
PRIMARY KEY (`id_alias`),
UNIQUE KEY `alias` (`alias`)
);
Elle permet de rediriger un terme vers un autre, ce qui couvre les synonymes courants et les fautes récurrentes de votre secteur. La limite est qu’il faut les saisir un par un, à la main, et donc les connaître à l’avance.
Quand un moteur dédié devient justifié
Une fois ces quatre points traités, la question devient légitime. Trois signaux, dans l’ordre où ils apparaissent.
Votre volume de mots indexés est important et vous avez plusieurs langues ou plusieurs boutiques. Vous êtes alors dans le régime où la recherche approximative est dégradée et où le coût des requêtes augmente.
Vos clients cherchent en langage naturel plutôt que par référence. Un index de mots avec des poids ne comprend pas une intention, il compte des occurrences.
Et surtout, vous ne savez pas ce que vos visiteurs cherchent. C’est le point le plus sous-estimé. Le moteur natif ne conserve pas d’historique exploitable des requêtes et de leurs résultats. Vous ignorez donc quelles recherches ne renvoient rien, et ce sont précisément celles qui coûtent des ventes.
Motive Commerce Search
C’est la solution que nous déployons chez nos clients quand ces signaux sont réunis, et pour laquelle nous sommes agence partenaire. Ce qu’elle apporte face aux limites décrites plus haut :
- Une tolérance aux fautes qui ne se dégrade pas avec la taille du catalogue, puisqu’elle ne repose pas sur un
LIKEet une comparaison de longueurs. - Une autocomplétion avec produits, qui raccourcit le chemin vers la fiche au lieu de passer par une page de résultats.
- La gestion des synonymes sans saisie manuelle exhaustive, là où les alias natifs demandent de connaître le terme à l’avance.
- Un rapport de requêtes, avec les recherches sans résultat. C’est le gain le plus immédiatement rentable, parce qu’il transforme un angle mort en liste d’actions : produits manquants, vocabulaire mal renseigné, catégories mal nommées.
Notre rôle sur ces projets est l’intégration technique dans la boutique, le paramétrage des règles métier et des pondérations, puis le suivi des rapports de requêtes pour ajuster dans la durée. Cette dernière partie compte autant que l’installation : un moteur de recherche se règle avec les données réelles de vos visiteurs, pas au moment de la mise en service.
Notre position
Nous commençons systématiquement par la requête de produits non indexés et par les quatre réglages gratuits. Sur une partie des boutiques qui nous consultent pour ce sujet, cela suffit, et nous le disons.
Quand cela ne suffit pas, la question n’est plus « le natif est-il limité » mais « combien me coûtent les recherches sans résultat ». C’est une question à laquelle on peut répondre avec des chiffres, et c’est sur ces chiffres que la décision doit se prendre.
Questions fréquentes
Ma recherche ne trouve pas un produit qui existe pourtant.
Vérifiez d’abord le drapeau d’indexation. La requête native impose product_shop.indexed = 1, et un produit non réindexé après un import est totalement absent des résultats, sans aucun message.
PrestaShop tolère-t-il les fautes de frappe ?
Oui, via une distance de Levenshtein activable. Mais uniquement en repli, quand la recherche exacte ne renvoie rien, et le cœur limite la comparaison aux mots de longueur identique dès que la table de mots devient volumineuse. La tolérance s’affaiblit donc à mesure que le catalogue grandit.
Pourquoi une recherche sur une référence courte ne renvoie rien ?
À cause de PS_SEARCH_MINWORDLEN, qui écarte les mots plus courts que le seuil avant même la requête. Le réglage est modifiable depuis le back-office.
Peut-on gérer des synonymes nativement ?
Oui, avec la table d’alias, qui redirige un terme vers un autre. La limite est qu’il faut les saisir manuellement, donc connaître à l’avance les termes employés par vos clients.
Un moteur externe améliore-t-il le référencement naturel ?
Pas directement. Il améliore le taux de conversion des visiteurs qui utilisent la recherche interne, ce qui est un tout autre levier. Ne l’achetez pas pour votre positionnement.
Par où commencer si ma recherche fonctionne mal ?
Par la requête des produits non indexés, puis par les pondérations et le seuil de longueur minimale. Ces trois vérifications prennent une heure et ne coûtent rien.
Votre recherche interne renvoie des résultats décevants et vous ne savez pas si c’est un réglage ou le moteur lui-même ? Lancez la requête des produits non indexés, c’est gratuit et c’est souvent la réponse. Si elle ne donne rien, parlons de ce que vos visiteurs cherchent réellement.


