問題描述

我需要在 post_title 上用 LIKE 做一個 WP_Query

我從這個常規 WP_Query 開始:

$wp_query = new WP_Query(
    array (
        'post_type'        => 'wp_exposants',
        'posts_per_page'   => '1',
        'post_status'      => 'publish',
        'orderby'          => 'title',
        'order'            => 'ASC',
        'paged'            => $paged
    )
);

但是我實際上想做的在 SQL 中看起來像這樣:

$query = "
        SELECT      *
        FROM        $wpdb->posts
        WHERE       $wpdb->posts.post_title LIKE '$param2%'
        AND         $wpdb->posts.post_type = 'wp_exposants'
        ORDER BY    $wpdb->posts.post_title
";
$wpdb->get_results($query);

輸出列印我正在研究的結果,但是我使用常規<?php while ( $wp_query->have_posts() ) : $wp_query->the_post(); ?> 來顯示結果。而這不適用於 $wpdb->get_results()

我怎麼能達到我在這裡描述的內容?

最佳解決方案

我會用 WP_Query 上的過濾器來解決這個問題。一個檢測額外的查詢變數並將其用作標題的字首。

add_filter( 'posts_where', 'wpse18703_posts_where', 10, 2 );
function wpse18703_posts_where( $where, &$wp_query )
{
    global $wpdb;
    if ( $wpse18703_title = $wp_query->get( 'wpse18703_title' ) ) {
        $where .= ' AND ' . $wpdb->posts . '.post_title LIKE '' . esc_sql( $wpdb->esc_like( $wpse18703_title ) ) . '%'';
    }
    return $where;
}

這樣,您仍然可以呼叫 WP_Query,您只需將標題作為 wpse18703_title 引數傳遞 (或將其更改為更短的名稱) 。

次佳解決方案

想要更新這個程式碼,你們為 4.0 以上的 wordpress 做了工作. esc_sql() 在 4.0 以後被棄用。

function title_filter($where, &$wp_query){
    global $wpdb;

    if($search_term = $wp_query->get( 'search_prod_title' )){
        /*using the esc_like() in here instead of other esc_sql()*/
        $search_term = $wpdb->esc_like($search_term);
        $search_term = ' '%' . $search_term . '%'';
        $where .= ' AND ' . $wpdb->posts . '.post_title LIKE '.$search_term;
    }

    return $where;
}

其餘的東西是一樣的。

另外我想指出你可以在 WP_Query 引數中使用 s 變數來傳遞搜尋項,這也將搜尋我相信的帖子標題。

喜歡這個:

$args = array(
    'post_type' => 'post',
    's' => $search_term,
    'post_status' => 'publish',
    'orderby'     => 'title',
    'order'       => 'ASC'
);
$wp_query = new WP_Query($args);

第三種解決方案

簡化:

function title_filter( $where, &$wp_query )
{
    global $wpdb;
    if ( $search_term = $wp_query->get( 'search_prod_title' ) ) {
        $where .= ' AND ' . $wpdb->posts . '.post_title LIKE '%' . esc_sql( like_escape( $search_term ) ) . '%'';
    }
    return $where;
}

$args = array(
    'post_type' => 'product',
    'posts_per_page' => $page_size,
    'paged' => $page,
    'search_prod_title' => $search_term,
    'post_status' => 'publish',
    'orderby'     => 'title',
    'order'       => 'ASC'
);

add_filter( 'posts_where', 'title_filter', 10, 2 );
$wp_query = new WP_Query($args);
remove_filter( 'posts_where', 'title_filter', 10, 2 );
return $wp_query;

第四種方案

在我之前的其他答案的基礎上,為了提供靈活性,您想要搜尋包含元欄位中的單詞或帖子標題的帖子,我透過引數”title_filter_relation.” 給出該選項在此實現中,我僅允許”OR” 或”AND” 輸入預設為”AND.”

function title_filter($where, &$wp_query){
    global $wpdb;
    if($search_term = $wp_query->get( 'title_filter' )){
        $search_term = $wpdb->esc_like($search_term); //instead of esc_sql()
        $search_term = ' '%' . $search_term . '%'';
        $title_filter_relation = (strtoupper($wp_query->get( 'title_filter_relation'))=='OR' ? 'OR' : 'AND');
        $where .= ' '.$title_filter_relation.' ' . $wpdb->posts . '.post_title LIKE '.$search_term;
    }
    return $where;
}

以下是一個非常簡單的帖子型別”faq” 的程式碼行為示例,其中問題是帖子標題本身:

add_filter('posts_where','title_filter',10,2);
$s1 = new WP_Query( array(
    'post_type' => 'faq',
    'posts_per_page' => -1,
    'title_filter' => $q,
    'title_filter_relation' => 'OR',
    'post_status' => 'publish',
    'orderby'     => 'title',
    'order'       => 'ASC',
    'meta_query' => array(
        'relation' => 'OR',
        array(
            'key' => 'faq_answer',
            'value' => $q,
            'compare' => 'LIKE'
        )
    )
));
remove_filter('posts_where','title_filter',10,2);

PS 。這是我在 wordpress 堆疊交換中的第一篇文章。

參考文獻

注:本文內容整合自 Google/Baidu/Bing 輔助翻譯的英文資料結果。如果您對結果不滿意,可以加入我們改善翻譯效果:薇曉朵技術論壇。