Минимизация запросов к базе данных при использовании расширенных настраиваемых полей
Я работаю над страницей, на которой перечислены сотрудники крупной компании, и пытаюсь свести к минимуму количество раз, когда я вынужден запрашивать базу данных, поскольку она становится довольно сложной и медленной.
-
'person'
- это пользовательский тип сообщения (около 300 человек) -
'date_accredited'
- это поле даты, добавленное с помощью плагина Расширенных пользовательских полей.
Только аккредитованный персонал будет иметь 'date_accredited'
.
Мне нужно перечислить всех 'person'
, НО со ВСЕМИ аккредитованными сотрудниками перечислены первыми (таким образом, около 20 аккредитованных сотрудников занимают первое место).
В данный момент я делаю вызов WP_Query, например:
$args = array(
'posts_per_page' => -1,
'post_type' => 'people',
'no_found_rows' => true,
'meta_key' => 'date_accredited'
);
$people = new WP_Query($args);
После этого я делаю:
while($people->have_posts()): $people->the_post();
$my_post_meta = get_post_meta($post->ID, 'date_accredited', true);
if (!empty($my_post_meta)) {
array_push($accredited, $post);
} else {
array_push($notAccredited, $post);
}
endwhile;
Оставляя нас с двумя массивами объектов "человек". Я думал здесь о том, что я мог бы сделать что-то вроде следующего, чтобы получить список, который я хочу:
foreach($accredited as $person):
personTile($person);
endforeach;
foreach($notAccredited as $person):
personTile($person);
endforeach;
Я пытаюсь избежать повторного запроса базы данных.
Функция personTile();
должна была выводить различную информацию и HTML (the_post_thumbnail()
и различные Расширенные поля настраиваемых полей), но сейчас я понимаю, что ничего из этого не включено в объекты post, которые я получаю от WP_Query()
, поэтому я вынужден использовать такие вещи, как:
get_the_post_thumbnail($person->ID)
get_permalink($person->ID)
-
get_field('date_accredited', $person->ID)
Все это стоит еще одного запроса к БД (каждый!), и что еще хуже, поскольку они находятся в цикле, каждый из них происходит около 300 раз.
Есть ли какой-либо способ включить поля постоянной ссылки, миниатюры и ACF в исходный запрос БД? Стал бы я нужно прибегнуть к пользовательскому запросу MySQL???
Любые другие предложения приветствуются!
1 answers
Все это стоит еще одного запроса к БД (каждый!), и что еще хуже, поскольку они находятся в цикле, каждый из них происходит около 300 раз.
Не паникуйте! Сообщения из вашего запроса хранятся в кэше объектов WordPress (это просто память, если у вас нет специальной системы кэширования).
Все функции, которые работают с сообщениями, проходят через этот кэш, поэтому в вашем случае нет дополнительного попадания в базу данных, даже если вы не находитесь в "цикле".
Ты однако вы захотите вставить эту строку сразу после вашего запроса:
// http://wpseek.com/function/update_post_thumbnail_cache/
update_post_thumbnail_cache( $people );
При этом будут запущены два дополнительных запроса (сообщения и мета-данные сообщений), которые добавят все эскизы (вложения) для сообщений в экземпляре WP_Query
в один и тот же кэш.
В противном случае вы получите множество запросов (по два для каждого сообщения с миниатюрой).
N.B: Есть несколько WP_Query
аргументов, которые изменят способ кэширования сообщений:
-
update_post_meta_cache
(почти всегда да) -
update_post_term_cache
(если вам не нужны термины, вы можете сохранить запрос здесь) -
fields
(если нетall
, то ничего не кэшируется и выше игнорируется) -
cache_results
(если значение false, то ничего не кэшируется и все вышеперечисленное игнорируется)