您不能在一个查询中完成此操作,这对于什么来说有点太高级了WP_Query
可以在此时完成。我们需要在这里运行至少两个(我将使用3个)查询来实现您想要的
第一次查询
第一次查询将根据
post_tag
, 这也将排除当前职位。我们将只获取帖子ID
第二个查询
此查询将处理来自
category
分类学要使此查询成功,我们需要以下内容
从第一次查询中排除当前帖子和帖子,以避免重复帖子
获取第一个查询中的帖子数量,从4中减去,然后使用该差异设置此查询应检索的帖子数量
我们还将在此处获取帖子ID
第三个查询
为了保持查询对象的完整性,我们将组合前一个查询中的所有ID,并查询最终的post对象。你可能认为这很贵,但事实并非如此。因为前两个查询使用
get_posts()
而且只获得帖子ID,它们真的非常快。通过只查询ID,我们也不会更新缓存,这使得这些查询更快
解决方案
我更喜欢为代码这样的大块创建一个函数,因为它可以保持我的模板干净。请注意,以下内容未经测试,需要PHP 5.4
function get_max_related_posts( $taxonomy_1 = \'post_tag\', $taxonomy_2 = \'category\', $total_posts = 4 )
{
// First, make sure we are on a single page, if not, bail
if ( !is_single() )
return false;
// Sanitize and vaidate our incoming data
if ( \'post_tag\' !== $taxonomy_1 ) {
$taxonomy_1 = filter_var( $taxonomy_1, FILTER_SANITIZE_STRING );
if ( !taxonomy_exists( $taxonomy_1 ) )
return false;
}
if ( \'category\' !== $taxonomy_2 ) {
$taxonomy_2 = filter_var( $taxonomy_2, FILTER_SANITIZE_STRING );
if ( !taxonomy_exists( $taxonomy_2 ) )
return false;
}
if ( 4 !== $total_posts ) {
$total_posts = filter_var( $total_posts, FILTER_VALIDATE_INT );
if ( !$total_posts )
return false;
}
// Everything checks out and is sanitized, lets get the current post
$current_post = sanitize_post( $GLOBALS[\'wp_the_query\']->get_queried_object() );
// Lets get the first taxonomy\'s terms belonging to the post
$terms_1 = get_the_terms( $current_post, $taxonomy_1 );
// Set a varaible to hold the post count from first query
$count = 0;
// Set a variable to hold the results from query 1
$q_1 = [];
// Make sure we have terms
if ( $terms_1 ) {
// Lets get the term ID\'s
$term_1_ids = wp_list_pluck( $terms_1, \'term_id\' );
// Lets build the query to get related posts
$args_1 = [
\'post_type\' => $current_post->post_type,
\'post__not_in\' => [$current_post->ID],
\'posts_per_page\' => $total_posts,
\'fields\' => \'ids\',
\'tax_query\' => [
[
\'taxonomy\' => $taxonomy_1,
\'terms\' => $term_1_ids,
\'include_children\' => false
]
],
];
$q_1 = get_posts( $args_1 );
// Count the total amount of posts
$q_1_count = count( $q_1 );
// Update our counter
$count = $q_1_count;
}
// We will now run the second query if $count is less than $total_posts
if ( $count < $total_posts ) {
$terms_2 = get_the_terms( $current_post, $taxonomy_2 );
// Make sure we have terms
if ( $terms_2 ) {
// Lets get the term ID\'s
$term_2_ids = wp_list_pluck( $terms_2, \'term_id\' );
// Calculate the amount of post to get
$diff = $total_posts - $count;
// Create an array of post ID\'s to exclude
if ( $q_1 ) {
$exclude = array_merge( [$current_post->ID], $q_1 );
} else {
$exclude = [$current_post->ID];
}
$args_2 = [
\'post_type\' => $current_post->post_type,
\'post__not_in\' => $exclude,
\'posts_per_page\' => $diff,
\'fields\' => \'ids\',
\'tax_query\' => [
[
\'taxonomy\' => $taxonomy_2,
\'terms\' => $term_2_ids,
\'include_children\' => false
]
],
];
$q_2 = get_posts( $args_2 );
if ( $q_2 ) {
// Merge the two results into one array of ID\'s
$q_1 = array_merge( $q_1, $q_2 );
}
}
}
// Make sure we have an array of ID\'s
if ( !$q_1 )
return false;
// Run our last query, and output the results
$final_args = [
\'ignore_sticky_posts\' => 1,
\'post_type\' => $current_post->post_type,
\'posts_per_page\' => count( $q_1 ),
\'post__in\' => $q_1,
\'order\' => \'ASC\',
\'orderby\' => \'post__in\',
\'suppress_filters\' => true,
\'no_found_rows\' => true
];
$final_query = new WP_Query( $final_args );
return $final_query;
}
现在,您可以在单个模板中使用以下函数
$query = get_max_related_posts();
if ( $query ) {
while ( $query->have_posts() ) {
$query->the_post();
echo get_the_title() . \'</br>\';
}
wp_reset_postdata();
}
少数注释默认值已设置为
post_tag
,
category
和
4
对于这三个参数,因此在调用函数时确实需要将任何值传递给函数
如果需要对分类法进行swop,或设置不同的分类法,或将每页的帖子设置为4以外的任何内容,只需按正确的顺序将它们传递给函数即可
$query = get_max_related_posts( \'tax_1\', \'tax_2\', 6 );