Как отсортировать функцию 'query_posts' по настраиваемому полю, при этом ограничение сообщений другим настраиваемым полем - PullRequest
1 голос
/ 06 ноября 2010

Я запрашиваю серию постов в WP со следующей функцией:

<?php 
$thirtydays = date('Y/m/d', strtotime('+30 days'));
$paged = (get_query_var('paged')) ? get_query_var('paged') : 1;
query_posts( array( 
    'post_type' => array('post', 'real-estate'), 
    'meta_key' => 'Time          Available', 
    'meta_compare' => '<=', 
    'meta_value' => $thirtydays, 
    'paged' => $paged )); 
?>

Эта часть работает нормально.Это в основном тянет все мои сообщения о недвижимости, но только возвращает результаты, у которых есть «Доступное время» 30 дней или меньше.

Мне нужно это также, чтобы упорядочить посты в порядке возрастания от низкого до высокого, используя данныеиз другого настраиваемого поля «Цена».

Всякий раз, когда я добавляю стандарт 'orderby' => 'meta_value', 'meta_key' => 'Price', он больше не показывает результаты в течение 30 дней.

Есть ли способ объединить эти два?И можно ли добавить кнопку, которая повторно запускает запрос и сортирует по цене, спальням и т. Д.?Или это слишком специфично для WP?

Ответы [ 2 ]

4 голосов
/ 06 ноября 2010

Я верю, что это даст вам желание, в котором вы нуждаетесь.Это класс с именем PostsOrderedByMetaQuery, который расширяет WP_Query и принимает новые аргументы 'orderby_meta_key' и 'orderby_order':

class PostsOrderedByMetaQuery extends WP_Query {
  var $posts_ordered_by_meta = true;
  var $orderby_order = 'ASC';
  var $orderby_meta_key;
  function __construct($args=array()) {
    add_filter('posts_join',array(&$this,'posts_join'),10,2);
    add_filter('posts_orderby',array(&$this,'posts_orderby'),10,2);
    $this->posts_ordered_by_meta = true;
    $this->orderby_meta_key = $args['orderby_meta_key'];
    unset($args['orderby_meta_key']);
    if (!empty($args['orderby_order'])) {
      $this->orderby_order = $args['orderby_order'];
      unset($args['orderby_order']);
    }
    parent::query($args);
  }
  function posts_join($join,$query) {
    if (isset($query->posts_ordered_by_meta)) {
      global $wpdb;
      $join .=<<<SQL
INNER JOIN {$wpdb->postmeta} postmeta_price ON postmeta_price.post_id={$wpdb->posts}.ID
       AND postmeta_price.meta_key='{$this->orderby_meta_key}'
SQL;
    }
    return $join;
  }
  function posts_orderby($orderby,$query) {
    if (isset($query->posts_ordered_by_meta)) {
      global $wpdb;
      $orderby = "postmeta_price.meta_value {$this->orderby_order}";
    }
    return $orderby;
  }
}

Вы бы назвали его так:

$thirtydays = date('Y/m/d', strtotime('+30 days'));
$paged = (get_query_var('paged')) ? get_query_var('paged') : 1;
$query = new PostsOrderedByMetaQuery(array(
  'post_type' => array('post', 'real-estate'),
  'meta_key' => 'Time Available',
  'meta_compare' => '<=',
  'meta_value' => $thirtydays,
  'paged' => $paged,
  'orderby_meta_key' => 'Price',
  'orderby_order'    => 'DESC',
));
foreach($query->posts as $post) {
  echo " {$post->post_title}\n";
}

Вы можете скопировать класс PostsOrderedByMetaQuery в файл functions.php вашей темы или использовать его в файле .php плагина, который вы, возможно, пишете.

Если вы хотите быстро его протестировать, я разместил автономную версию кода на Gist, которую вы можете скачать и скопировать в корневой каталог вашего веб-сервера.как test.php, измените для своего варианта использования, а затем запросите в браузере URL-адрес, например http://example.com/test.php.

Надеюсь, это поможет.

-Mike

PSЭтот ответ очень похож на ответ, который я только что дал на WordPress Ответы , который является дочерним сайтом StackOverflow, где многие энтузиасты WordPress, такие как я, ежедневно отвечают на вопросы.Возможно, вы захотите увидеть этот ответ тоже , потому что он содержит чуть больше объяснений и потому что вы можете захотеть увидеть Ответы WordPress .Надеюсь, вы рассмотрите возможность размещения своих вопросов WordPress на там тоже в будущем?

0 голосов
/ 06 ноября 2010

Поскольку 'orderby' => 'meta_value' требует meta_key, а ваш meta_key уже используется для сравнения, я не думаю, что вы можете сделать это. meta_key принимает только одно значение, а не массив опций. Это определенно ограничение, и я призываю вас открыть запрос, если вы не нашли решение.

Что касается кнопки для повторного запуска запроса, вы можете просто перезагрузить страницу и передать переменную запроса, чтобы изменить сортировку. К сожалению, вам еще предстоит решить первую часть вашего вопроса.

UPDATE

Вы всегда можете отсортировать возвращаемый массив самостоятельно, используя PHP.

Кроме того, не уверены, что вы проверяете с доступным временем, но вы можете зарегистрировать фильтр, который поможет вам настроить запрос немного дальше add_filter('posts_where', ...); http://codex.wordpress.org/Function_Reference/query_posts

...