Вы используйте аргумент post__not_in
для исключения постов? Фатальная ошибка!
Аргумент WP_Query post__not_in
кажется полезным, но представьте себе, он может привести к увеличению скорости загрузки вашего блога.
post__not_in
используется для исключения записей из результатов запроса. Например, у вас цикл, который показывает 5 свежих записей на странице открытого поста - к примеру как страница которую вы сейчас читаете, то вам не нужно выводить текущий пост в результате похожих постов, поскольку вы уже читает эту статью.
Ваш цикл с post__not_in
Представим что ваш цикл с удалением лишних постов выглядт вот так:
function the_recent_news($exclude = []) {
$args = array(
'category_name' => 'news',
'post_type' => 'articles',
'posts_per_page' => 5,
'post_status' => 'publish',
'post__not_in' => $exclude
);
$result_posts = new WP_Query($args);
echo '<div class="recent-news"><h1>News:</h1>';
while ($result_posts->have_posts()) {
$result_posts->the_post();
the_title('<h2><a href="' . get_permalink() . '">', '</a></h2>');
}
echo '</div>';
wp_reset_postdata();
}
// Вызов
the_recent_news([get_the_ID()]);
При вызове нашей функции она выведет 5 последних записей без текущего поста. Это легко, но пагубно влияет на скорость.
Почему post__not_in
вреден?
Запрос, который раньше использовал встроенный кеш запросов, теперь "Уникален" для каждой страницы, на которой вызывается функция )"]. Благодаря добавлению AND ID not in ( '777' )
в SQL запрос.
Это как подъём гантелей в мире программирования - если не распределить нагрузку, можно получить 'мышечное завтра' для компьютера!
Это связано с тем, что ключ кэша, который представляет собой хеш аргументов, теперь включает список как минимум из одного идентификатора, и он разный для всех страниц.
К примеру так выглядит хеш при выводе постов post_type_article
. Он кешируется при первом вызове и в дальнейшем будет показываться из кеша. Но при добавлении post__not_in
мы имеем фактор уникальности в виде исключаемого ID поста и хеш на странице "777" будет выглядит так: post_type_article_not_in_777
Из-за примера выше, вместо того чтобы остальные страницы получали список из кэша объектов, он пропустит кеш, и база данных будет выполнять ту же работу на нескольких страницах.
В результате каждый из этих запросов теперь кэшируется отдельно.
Как исправить плохой цикл?
Для повышения скорости загрузки сайта рекомендую использовать единообразие запроса, post__not_in
заменить на проверку в результате цикла.
Используйте в posts_per_page
фиксированное число а не переменную, чтобы уменьшить количество вариантов кеша.
Мы увечили posts_per_page
до 6, т.к 1 из постов будет убран
Обновленная функция исключает пост в ходе цикла а не исключает его в SQL, пример:
function the_recent_news($exclude = []) {
$args = array(
'category_name' => 'news',
'post_type' => 'articles',
'posts_per_page' => 6,
'post_status' => 'publish',
);
$result_posts = new WP_Query($args);
echo '<div class="recent-news"><h1>News:</h1>';
$i = 0;
while ( $result_posts->have_posts() and $i < 5 ) {
$result_posts->the_post();
$post_id = get_the_ID();
if ( ! in_array( $post_id, $exclude ) ) {
the_title( '<h2><a href="' . get_permalink() . '">', '</a></h2>');
$i++;
}
}
echo '</div>';
wp_reset_postdata();
}
// Вызов
the_recent_news([get_the_ID()]);
Не смотря на увеличение количества кода и требование логики PHP, наш метод лучше т.к он использует кеш запросов и позволяет избежать создания множества вариантов кеша, которые могут повлиять на масштабируемость и стабильность сайта.
Что такое аргумент post__not_in в wp_query?
Аргумент post__not_in в WordPress используется для исключения определенных записей из результатов запроса.