В WP есть универсальная функция «get_posts», но она к сожалению не подходит во всех 100% случаях. Иногда, что бы получить нужный результат, приходится формировать SQL запрос вручную. Я не особо люблю этого делать, т. к. всех тонкостей и нюансов подкапотной работы ВП мне не известны (где и в каких случаях лучше вставлять нужные фильтры). Но задачу реализовать нужно, и приходится создавать свой SQL.
На этот раз нужно было отобразить список постов, отсортировав их таким образом, чтобы пост с последним добавленным и одобренным комментарием отображался вначале. По мере убывания, свежие — раньше, менее свежие — в конце.
Для этого пишем следующий sql запрос и php код:
global $wpdb; $sql = "SELECT `p`.ID, `cl`.`comment_date_last` FROM {$wpdb -> posts} `p` INNER JOIN ( SELECT `comment_post_ID`, MAX(comment_date) `comment_date_last` FROM {$wpdb -> comments} `c` WHERE `comment_approved` = 1 GROUP BY `comment_post_ID` ) `cl` ON (`cl`.`comment_post_ID`=`p`.`ID`) WHERE `p`.post_type = 'post' AND `p`.post_status = 'publish' ORDER BY `comment_date_last` DESC"; $posts_ar = $wpdb -> get_results($sql, ARRAY_A); foreach($posts_ar as $post_ar): echo $post_ar['ID']; /* … */ endforeach;
Первое что нам нужно, это вызвать глобальный объект работы с БД в WordPress — «$wpdb».
Далее идет запрос, он состоит из двух частей:
- Основной запрос, с выборкой данных из таблицы постов.
- Подзапрос с ограничением «INNER JOIN», что позволит нам отобразить только те посты, у которых есть комментарии. В подзапросе, мы выбираем посты с самым последним комментарием. Для этого используем функцию «MAX()». А для соединения подзапроса с основным, добавляем в выборку поле «comment_post_ID».
Используя «WHERE», мы ограничиваем выборку по основному запросу постами (`p`.post_type = 'post') и статусом «publish» (`p`.post_status = 'publish'). Ну и конечно же сортируем все по датам комментариев «ORDER BY `comment_date_last` DESC»
Ну а сам список постов отображаем через цикл PHP ф-и «foreach»:
foreach($posts_ar as $post_ar): echo $post_ar['ID']; /* … */ endforeach;
В коде выше, мы лишь выводим на экран ID поста. Но его можно передавать в такие WP функции как — get_the_title(), get_permalink() и многие другие.