Вопрос или проблема
Я прочитал всю документацию по WordPress, которая кажется актуальной, и прочитал много постов здесь и на других сайтах, чтобы найти ответ на это, но все равно не могу найти способ сделать это.
У меня есть пользовательский тип записи. У моего пользовательского типа записи есть метаданные. Одно из этих полей метаданных является булевым (1 или 0), под названием ‘featured’, который действует как флаг. Я пытаюсь создать запрос для query_posts() (я соглашусь на WP_Query, если придется), который сначала вернет записи с установленным флагом (отсортированные по дате или ID записи DESC), а затем записи, у которых флаг не установлен (и их также отсортировать по дате или ID записи DESC).
Цель заключается в том, чтобы выбрать рекомендованные записи в верхней части списка, отсортированные по дате публикации, с самыми последними записями первыми, а затем обычные записи, также отсортированные по дате публикации, с самыми последними записями первыми.
Например:
a: ID=800, featured=1
b: ID=801, featured=0
c: ID=802, featured=0
d: ID=803, featured=1
e: ID=804, featured=0
Этот список записей должен быть возвращен мне в следующем порядке: d, a, e, c, b
Вместо этого я получаю: a, d, b, c, e
Вот код запроса, который у меня есть на данный момент:
$query = query_posts( array(
'post_type' => 'my_custom_type',
'post_status' => 'publish',
'posts_per_page' => '9',
'orderby' => array(
'meta_value_num' => 'DESC',
'post_ID' => 'DESC'
),
'meta_key' => 'featured'
) );
Я пробовал всевозможные варианты на тему orderby. Сначала я пытался отсортировать по дате публикации, но затем попробовал ID записи, так как он должен возвращать тот же порядок и является простым целым числом. Я изменял DESC на ASC и обратно, добавлял фильтры, которые видел в других постах… что бы я ни делал, после первоначальной сортировки по флагу записи всегда находятся в порядке ASC (то есть ASC по ID записи или ASC по дате записи).
Пожалуйста, помогите!!
Я продолжал исследовать свою проблему и в итоге нашел решение здесь: Мне нужно, чтобы query_posts() сортировал результаты сначала по мета-значению, а затем по ID записи
В основном, кажется, что порядок WordPress испорчен. Когда я исследовал SQL, который он генерировал, orderby выглядел так:
ORDER BY wppc_postmeta.meta_value+0 DESC
Что по сути не имеет смысла.
Поэтому я создал быструю функцию фильтра, чтобы записать код orderby так, как WordPress должен был это сделать с самого начала:
function pb_override_orderby() {
$orderby_statement = "wppc_postmeta.meta_value DESC, wppc_posts.post_date_gmt DESC";
return $orderby_statement;
}
Затем, сразу перед тем, как я вызываю query_posts(), я добавляю строку:
add_filter('posts_orderby', 'pb_override_orderby');
Эти два фрагмента выбрасывают плохой код WordPress и заменяют его на правильный код, который работает как необходимо. Намного лучше. Что-то, на что WordPress должен обратить внимание в каком-то будущем исправлении ошибок.
Ответ или решение
Понимаю вашу задачу, и рад, что вы нашли решение к вашей проблеме с сортировкой постов в WordPress. Давайте подробнее разберем ваш вопрос, чтобы обеспечить полное понимание и правильное применение решения.
Проблематика
Вы работаете с пользовательским типом поста в WordPress, который содержит метаданные, включая логическое поле featured
. Вам необходимо сортировать посты так, чтобы сначала отображались те, у которых установлено это поле (значение 1), а затем посты с полем, равным 0. При этом посты должны быть отсортированы по дате публикации в порядке убывания, что весьма распространенный подход для таких сценариев.
Текущий код, который вы использовали с query_posts()
, не давал ожидаемых результатов по причине некорректной логики формирования SQL-запроса в WordPress, как вы сами установили.
Решение
Вы правильно выбрали подход с использованием функции add_filter
для переопределения SQL-запроса. Ниже приведу детальное объяснение вашего решения и его составляющие.
Шаг 1: Создание функции для переопределения ORDER BY
Вы создали функцию pb_override_orderby
, которая возвращает правильное выражение для сортировки:
function pb_override_orderby($orderby) {
// Переопределяем порядок сортировки
$orderby = "wppc_postmeta.meta_value DESC, wppc_posts.post_date_gmt DESC";
return $orderby;
}
Этот код переопределяет порядок сортировки, чтобы сначала учитывать значение мета-поля featured
, а затем дату публикации постов.
Шаг 2: Применение фильтра перед выполнением запроса
Ваша логика применения фильтра перед выполнением запроса выглядит следующим образом:
add_filter('posts_orderby', 'pb_override_orderby');
$query = query_posts(array(
'post_type' => 'my_custom_type',
'post_status' => 'publish',
'posts_per_page' => '9',
'meta_key' => 'featured',
));
Таким образом, при выполнении запроса query_posts
, WordPress будет использовать ваше определение порядка сортировки.
Итог
Ваше решение эффективно и предоставляет ожидаемый результат: сначала будут показаны посты с мета-значением featured = 1
, а затем с featured = 0
, оба набора отсортированы по дате публикации. Это подход позволяет обойти ограничения стандартных функций WordPress и настроить SQL-запрос под ваши нужды.
Не забывайте, что в случае дальнейших обновлений WordPress нужно будет возможно проверить работоспособность вашего кода, так как изменения в ядре CMS могут влиять на работу фильтров и запросов. Обращайте внимание на документацию и возможные лучшие практики.
Если у вас есть дополнительные вопросы или нужна помощь в других аспектах WordPress разработки, не стесняйтесь обращаться!