web-dev-qa-db-ja.com

を使う OR query_posts引数に対するmeta_queryの条件

私はこれについて高低を検索しましたが、私は何かを見つけることができないようです。

私はいくつかの結果をフィルタしようとしていて、このようにargs配列を作成してquery_postsに渡すと、生成されたSQLは 'class_1_days'値にORではなくANDを使用します。 ORよりも作りたいのですが。これをどのようにして行うのでしょうか。 (データがシリアル化されているので、そこでLIKEを使用しています。それ以外の場合は、 "IN"を試して配列を渡すことになります。これを回避するための適切な方法は何ですか?

$args = array(
            'taxonomy' => 'courses', 
            'term' => 'drawing', 
            'post_type' => 'school', 
            'paged' => $paged,
            'meta_query' =>
                #$checkbox_array,
                array(
                    array(
                        'key' => 'instructor',
                        'value' => '1128',
                        'compare' => 'LIKE',
                    ),
                    array(
                        'key' => 'class_1_days',
                        'value' => 'Friday',
                        'compare' => 'LIKE',
                    ),
                    array(
                        'key' => 'class_1_days',
                        'value' => 'Saturday',
                        'compare' => 'LIKE',
                    ),
                )

        );

これは、ANDに気づいた場所で生成されている関連SQLです。

[138] => Array
    (
        [0] => SELECT SQL_CALC_FOUND_ROWS  wp_posts.ID FROM wp_posts  INNER JOIN     wp_term_relationships ON (wp_posts.ID = wp_term_relationships.object_id) INNER JOIN     wp_postmeta ON (wp_posts.ID = wp_postmeta.post_id)
INNER JOIN wp_postmeta AS mt1 ON (wp_posts.ID = mt1.post_id)
INNER JOIN wp_postmeta AS mt2 ON (wp_posts.ID = mt2.post_id) WHERE 1=1  AND (     wp_term_relationships.term_taxonomy_id IN (18) ) AND wp_posts.post_type = 'school' AND     (wp_posts.post_status = 'publish' OR wp_posts.post_status = 'private') AND (     (wp_postmeta.meta_key = 'instructor' AND CAST(wp_postmeta.meta_value AS CHAR) LIKE '%1128%')
AND  (mt1.meta_key = 'class_1_days' AND CAST(mt1.meta_value AS CHAR) LIKE '%Friday%')
AND  (mt2.meta_key = 'class_1_days' AND CAST(mt2.meta_value AS CHAR) LIKE '%Saturday%') ) GROUP BY wp_posts.ID ORDER BY wp_posts.post_date DESC LIMIT 0, 5
3
Devario Johnson

以下の'relation' => 'OR'Codexの例のように を使用してください。

$args = array(
    'post_type' => 'product',
    'meta_query' => array(
        'relation' => 'OR', /* <-- here */
        array(
            'key' => 'color',
            'value' => 'blue',
            'compare' => 'NOT LIKE'
        ),
        array(
            'key' => 'price',
            'value' => array( 20, 100 ),
            'type' => 'numeric',
            'compare' => 'BETWEEN'
        )
    )
);
$query = new WP_Query( $args );

それはあなたのすべてのmeta_queryブロックにわたってあなたにORを与えるでしょう。あなたが必要としているものがWHERE "instructor" = 1128 AND (class_1_days = "value1" OR class_1_days = "value2")のようなものであるならば、あなたのデータが直列化されていないならば、このようなものはそれをするでしょう。

$args = array(
        'taxonomy' => 'courses', 
        'term' => 'drawing', 
        'post_type' => 'school', 
        'paged' => $paged,
        'meta_query' =>
            array(
                array(
                    'key' => 'instructor',
                    'value' => '1128',
                    'compare' => 'LIKE',
                ),
                array(
                    'key' => 'class_1_days',
                    'value' => array('Friday','Saturday')
                    'compare' => 'IN',
                )
            )

    );

データをシリアル化したことを考えると、これは困難になります。あなたはposts_whereのためのフィルタを書くことができますが、私は結果が非効率的でエラーを起こしやすいと思います。

私の経験では、最初の段階でデータを直列化された配列として格納しないことが、情報の一部で検索/フィルタ処理/並べ替えを行う必要がある場合の正しい方法です。このようなクエリが必要な場合、これは単に間違ったアプローチです。

このプロジェクトを引き継いでいるのであれば、この方法で照会する必要があるデータをループ処理して、キーと値のペアで各部分を再保存します。照会していない部分は直列化されたままになります。あなたが試みている問い合わせの一部としても、あるいは何らかの独立した問い合わせとしても、MySQL関数を使ってMySQLにこれをする(良い)方法はありません。 MySQLの "unserialize"関数を作成しようとしましたが、その点はわかりません。データを再保存することは行くべき方法です。

すべてのclass_1_daysデータを取得するのはかなり単純なクエリであるべきです。それからそれをループし、あなたが独立したキーとして問い合わせる必要がある部分を保存して、シリアル化されたデータとして戻します。

2
s_ha_dum