WP_Query — это мощный класс WordPress, который позволяет гибко получать и выводить записи из базы данных. Однако часто стандартных параметров недостаточно, и возникает необходимость создавать собственные фильтры для сортировки, поиска и отображения постов по определённым условиям. В этой статье мы подробно разберём, как создавать такие фильтры, используя возможности WP_Query и хуков WordPress.
Что такое WP_Query и зачем нужны кастомные фильтры
WP_Query — это объектно-ориентированный интерфейс для выборки постов. С его помощью можно задать параметры, например, категорию, дату, количество постов и многое другое. Но что если нужно фильтровать записи по нестандартным мета-полям, объединять несколько условий или изменять SQL-запросы? Здесь на помощь приходят кастомные фильтры.
Кастомные фильтры позволяют расширять стандартный функционал, добавляя свои аргументы, изменяя запросы на уровне SQL, или модифицируя результаты выборки. Это особенно полезно при разработке сложных каталогов, интернет-магазинов и сайтов с уникальной логикой отбора контента.
Пример типичной задачи — вывести записи, где мета-поле «цена» меньше заданного значения и сортировать их по рейтингу, хранящемуся в другом мета-поле.
Использование параметра meta_query для фильтрации по мета-полям
Один из самых популярных способов фильтрации — использовать параметр meta_query. Он позволяет строить сложные условия для мета-полей, используя операторы сравнения и логические связи.
Пример запроса, который получает все посты типа product, у которых цена меньше 1000 и рейтинг выше 4:
$args = [
'post_type' => 'product',
'meta_query' => [
'relation' => 'AND',
[
'key' => 'wptasks_price',
'value' => 1000,
'type' => 'NUMERIC',
'compare' => '<'
],
[
'key' => 'wptasks_rating',
'value' => 4,
'type' => 'NUMERIC',
'compare' => '>'
]
]
];
$query = new WP_Query($args);Обратите внимание, что для корректной работы числовых сравнений обязательно указывать параметр type — иначе сравнение будет строковым.
Можно использовать также relation, чтобы объединять условия через AND или OR.
Динамические фильтры из пользовательского интерфейса
Часто фильтры строятся по пользовательскому вводу — например, значения из формы на сайте. В этом случае нужно аккуратно обрабатывать входящие параметры и формировать meta_query динамически.
Пример функции для формирования фильтра по цене из GET-параметров:
function wptasks_build_price_filter() {
$meta_query = [];
if (!empty($_GET['max_price'])) {
$max_price = intval($_GET['max_price']);
$meta_query[] = [
'key' => 'wptasks_price',
'value' => $max_price,
'type' => 'NUMERIC',
'compare' => '<='
];
}
if (!empty($_GET['min_price'])) {
$min_price = intval($_GET['min_price']);
$meta_query[] = [
'key' => 'wptasks_price',
'value' => $min_price,
'type' => 'NUMERIC',
'compare' => '>='
];
}
return $meta_query;
}Далее используйте эту функцию при формировании аргументов для WP_Query.
Расширение WP_Query с помощью фильтра pre_get_posts
Чтобы изменить параметры запроса глобально или для определённых страниц, используется хук pre_get_posts. Он позволяет менять аргументы запроса до его выполнения.
Пример — добавим фильтр, который на главной странице сайта выводит только записи с рейтингом выше 3:
add_action('pre_get_posts', 'wptasks_filter_main_query');
function wptasks_filter_main_query($query) {
if (is_admin() || !$query->is_main_query()) {
return;
}
if (is_home()) {
$meta_query = [
[
'key' => 'wptasks_rating',
'value' => 3,
'type' => 'NUMERIC',
'compare' => '>'
]
];
$query->set('meta_query', $meta_query);
}
}Таким образом, мы можем легко влиять на любое стандартное или кастомное представление контента без изменения шаблонов.
Создание собственных параметров запроса с помощью фильтра query_vars
Иногда хочется, чтобы в URL можно было передавать свои параметры фильтра, например ?wptasks_min_price=500, и чтобы WP_Query их автоматически понимал.
Для этого нужно добавить свои переменные в список разрешённых через фильтр query_vars и потом использовать их в pre_get_posts.
add_filter('query_vars', 'wptasks_add_query_vars');
function wptasks_add_query_vars($vars) {
$vars[] = 'wptasks_min_price';
$vars[] = 'wptasks_max_price';
return $vars;
}
add_action('pre_get_posts', 'wptasks_apply_custom_filters');
function wptasks_apply_custom_filters($query) {
if (is_admin() || !$query->is_main_query()) {
return;
}
$min_price = get_query_var('wptasks_min_price');
$max_price = get_query_var('wptasks_max_price');
$meta_query = [];
if ($min_price !== '') {
$meta_query[] = [
'key' => 'wptasks_price',
'value' => intval($min_price),
'type' => 'NUMERIC',
'compare' => '>='
];
}
if ($max_price !== '') {
$meta_query[] = [
'key' => 'wptasks_price',
'value' => intval($max_price),
'type' => 'NUMERIC',
'compare' => '<='
];
}
if (!empty($meta_query)) {
$query->set('meta_query', $meta_query);
}
}Теперь пользователь может фильтровать записи через URL, например: https://site.ru/?wptasks_min_price=500&wptasks_max_price=1500.
Примеры полезных плагинов для расширения фильтров WP_Query
Если хочется не писать весь код вручную, можно использовать готовые решения. Вот несколько популярных плагинов для фильтрации контента:
- FacetWP — очень мощный и удобный плагин для создания фильтров и фасетов по таксономиям, мета-полям, пользовательским полям.
- Search & Filter — позволяет строить сложные фильтры с визуальным редактором, интегрируется с WP_Query.
- WP Smart Filters — хороший инструмент для AJAX фильтрации и сортировки записей.
Все эти плагины используют под капотом WP_Query и позволяют быстро создавать пользовательские интерфейсы фильтрации без глубоких знаний PHP.
Советы по оптимизации фильтров WP_Query
При работе с фильтрами нужно помнить о производительности. Запросы с множеством meta_query могут сильно нагружать базу данных.
Рекомендации:
- Используйте индексы на мета-полях, если фильтруете по ним часто.
- Минимизируйте количество условий и избегайте сложных «OR» связок.
- Кэшируйте результаты запросов, используя Transients API или внешние кэши.
- Используйте AJAX-загрузку для крупных списков, чтобы не перегружать страницу.
Эти простые шаги помогут сделать сайт быстрым и отзывчивым даже при сложной логике фильтрации.
Заключение: гибкость и мощь фильтров WP_Query
Фильтры WP_Query — это ключевой инструмент для кастомизации вывода контента в WordPress. Они позволяют создавать уникальные страницы с динамическим выбором записей, подстраиваясь под любые бизнес-задачи.
Используя meta_query, pre_get_posts, query_vars и другие хуки, вы можете реализовать практически любые фильтры, которые только нужны вашему проекту. А если хочется ускорить разработку, всегда можно обратиться к мощным плагинам для фильтрации.
Освоив эти техники, вы сможете создавать профессиональные и удобные интерфейсы для пользователей, значительно расширяя функционал своих сайтов на WordPress.