รุ่นของรหัสที่นี่ในสองสามคำตอบที่ปรับเปลี่ยนพารามิเตอร์ meta_query ของ WP_Query ของการค้นหาใน pre_get_posts ไม่ได้ค้นหา post_title อีกต่อไป การเพิ่มความสามารถในการค้นหาทั้งชื่อโพสต์หรือค่าเมตาไม่สามารถทำได้โดยตรงใน WP_Query โดยไม่ต้องแก้ไข SQL โชคไม่ดีเนื่องจากคำถามนี้มีความละเอียดเมื่อ: การใช้แบบสอบถาม meta ('meta_query') กับคำค้นหา ('s)
ฉันได้รวมเทคนิคบางอย่างที่นี่เพื่อรับรุ่นทำงานที่หลีกเลี่ยง preg_replaces และการดัดแปลง SQL มากเกินไป (ฉันหวังว่ามันจะสามารถหลีกเลี่ยงได้ทั้งหมด) ข้อเสียเพียงอย่างเดียวคือหลังจากค้นหาข้อความคำบรรยายที่ด้านบนของหน้าระบุว่า "ผลการค้นหาสำหรับ ''" ฉันเพิ่งซ่อนด้วย CSS สำหรับประเภทโพสต์ที่กำหนดเองของปลั๊กอิน
/**
* Extend custom post type search to also search meta fields
* @param WP_Query $query
*/
function extend_cpt_admin_search( $query ) {
// Make sure we're in the admin area and that this is our custom post type
if ( !is_admin() || $query->query['post_type'] != 'your_custom_post_type' ){
return;
}
// Put all the meta fields you want to search for here
$custom_fields = array(
"your_custom_meta_field",
"your_custom_meta_field2",
"your_custom_meta_field3"
);
// The string submitted via the search form
$searchterm = $query->query_vars['s'];
// Set to empty, otherwise no results will be returned.
// The one downside is that the displayed search text is empty at the top of the page.
$query->query_vars['s'] = '';
if ($searchterm != ""){
// Add additional meta_query parameter to the WP_Query object.
// Reference: https://codex.wordpress.org/Class_Reference/WP_Query#Custom_Field_Parameters
$meta_query = array();
foreach($custom_fields as $cf) {
array_push($meta_query, array(
'key' => $cf,
'value' => $searchterm,
'compare' => 'LIKE'
));
}
// Use an 'OR' comparison for each additional custom meta field.
if (count($meta_query) > 1){
$meta_query['relation'] = 'OR';
}
// Set the meta_query parameter
$query->set('meta_query', $meta_query);
// To allow the search to also return "OR" results on the post_title
$query->set('_meta_or_title', $searchterm);
}
}
add_action('pre_get_posts', 'extend_cpt_admin_search');
/**
* WP_Query parameter _meta_or_title to allow searching post_title when also
* checking searching custom meta values
* https://wordpress.stackexchange.com/questions/78649/using-meta-query-meta-query-with-a-search-query-s
* https://wordpress.stackexchange.com/a/178492
* This looks a little scary, but basically it's modifying the WHERE clause in the
* SQL to say "[like the post_title] OR [the existing WHERE clause]"
* @param WP_Query $q
*/
function meta_or_title_search( $q ){
if( $title = $q->get( '_meta_or_title' ) ){
add_filter( 'get_meta_sql', function( $sql ) use ( $title ){
global $wpdb;
// Only run once:
static $nr = 0;
if( 0 != $nr++ ) return $sql;
// Modified WHERE
$sql['where'] = sprintf(
" AND ( (%s) OR (%s) ) ",
$wpdb->prepare( "{$wpdb->posts}.post_title LIKE '%%%s%%'", $title),
mb_substr( $sql['where'], 5, mb_strlen( $sql['where'] ) )
);
return $sql;
});
}
}
add_action('pre_get_posts', 'meta_or_title_search');