web-dev-qa-db-fra.com

Exécuter un grand WP_Query avec plusieurs "AND" Meta_Queries?

J'ai un type de message personnalisé product. Les visiteurs peuvent rechercher products avec de nombreux filtres. Ils peuvent définir la color, la size, la price, etc. Les détails du produit sont stockés avec Champs personnalisés avancés (ACF) .

Ma solution était un WP_Query avec meta_queries. Tous les WP_Meta_Queries sont dans des relations AND-.

Mon problème est le suivant: si le visiteur crée plus de filtres pour le produit, la requête sera toujours plus lente. Je pense que le INNER JOINs sur wp_postmeta est le problème. J'ai six INNER JOINs sur cette table.

Existe-t-il une solution à ce problème?

4
poldixd

Vous pourriez avoir besoin d’une solution à 180 ° ici;) Pensez une fois de plus au problème et essayez ceci:

En tant que visiteur, je peux filtrer par couleur et par taille.

Donc, votre solution pourrait être:

...
JOIN ... (A)
... (B)
... (C)
WHERE (A.meta_key = 'color' AND A.meta_value = 'red')
OR (B.meta_key = 'color' AND B.meta_value = 'blue')
...
AND (C.meta_key = 'size' AND C.meta_value = 1)
...

Mais en réalité, vous pouvez supprimer certaines jointures en utilisant IN:

JOIN ... (A)
... (B)
WHERE (A.meta_key = 'color' AND A.meta_value IN ('red', 'yellow'))
AND (B.meta_key = 'size' AND B.meta_value IN (1, 2, 3))

Alors commencez à utiliser "IN" pour comparer les valeurs comme dans le manuel :

$args = array(
    'post_type'  => 'my_custom_post_type',
    'meta_key'   => 'age',
    'orderby'    => 'meta_value_num',
    'order'      => 'ASC',
    'meta_query' => array(
        array(
            'key'     => 'age',
            'value'   => array( 3, 4 ),
            'compare' => 'IN',
        ),
    ),
);
$query = new WP_Query( $args );

Vous pouvez même commencer à deviner et l’avoir avec seulement une ou aucune jointure:

WHERE meta_key IN ('color', 'size')
  AND meta_value IN ('red', 'blue', 123, 45)

Ce serait rapide, mais pourrait aboutir à beaucoup de faux positifs.

6
LeMike