我正在尝试添加到WP搜索中,以便它包含一些元字段。这是我当前的代码functions.php
这是基于几年前的另一个堆栈:
function extend_search_query($query) {
if ($query->is_search) {
$query->set(\'meta_query\', [
\'relation\' => \'OR\',
[
\'key\' => \'ean\',
\'value\' => filter_var($query->query_vars[\'s\'], FILTER_SANITIZE_STRING),
\'compare\' => \'LIKE\',
],[
\'key\' => \'product_code\',
\'value\' => filter_var($query->query_vars[\'s\'], FILTER_SANITIZE_STRING),
\'compare\' => \'LIKE\',
]
]);
};
}
add_filter(\'pre_get_posts\', \'extend_search_query\');
执行此操作时,搜索不会返回任何类型搜索的结果。本质上,我只想检查这些字段,如帖子标题和内容等。
我确实尝试将其作为meta_query
在args中,但再次发现这与搜索有关。
谢谢
最合适的回答,由SO网友:Krzysiek Dróżdż 整理而成
您的查询有一个问题。您假设它将使用OR
与所有查询部件的关系。但不会。OR运算符将仅用于meta\\u查询部分。
这意味着您的查询正在查找符合以下条件的帖子:
(post_title LIKE query) AND ( ean LIKE query OR product_code LIKE query )
因此,如果您要搜索EAN,则不会找到任何结果,因为没有产品的标题中包含EAN。如果您要搜索任何单词,那么它也不会返回任何结果,因为没有产品会在EAN或product\\u代码字段中包含该单词。
So is it possible to search like that? And how to?
是的,是的。一种方法是添加以下过滤器:
function search_by_meta_join( $join ) {
global $wpdb;
if ( is_search() ) {
$join .= " LEFT JOIN {$wpdb->postmeta} pm_ean ON {$wpdb->posts}.ID = pm_ean.post_id AND (pm_ean.meta_key = \'ean\') ";
$join .= " LEFT JOIN {$wpdb->postmeta} pm_code ON {$wpdb->posts}.ID = pm_code.post_id AND (pm_code.meta_key = \'product_code\') ";
}
return $join;
}
add_filter(\'posts_join\', \'search_by_meta_join\' );
function search_by_meta_where( $where ) {
global $wpdb;
if ( is_search() ) {
$where = preg_replace(
"/\\(\\s*{$wpdb->posts}.post_title\\s+LIKE\\s*(\\\'[^\\\']+\\\')\\s*\\)/",
"({$wpdb->posts}.post_title LIKE $1) OR (pm_ean.meta_value LIKE $1) OR (pm_code.meta_value LIKE $1) ", $where );
}
return $where;
}
add_filter( \'posts_where\', \'search_by_meta_where\' );