как правильно сравнивать даты в мета-запросе WP-запросов
У меня есть вызов query_posts в шаблоне WP. С помощью плагина "Больше полей" я могу предоставить администратору сайта возможность создавать событие (пользовательский тип записи), а затем вводить дату в формате: ГГГГ/мм/дд.
Главный вопрос заключается в следующем: какое значение я должен передать параметру value в массиве meta_query? В настоящее время я пытаюсь передать "дату ("Y/m/d h: i A")" (за вычетом кавычек), потому что, как я понимаю, это выведет текущую дату сегодня. Я не заботьтесь о времени свидания, так что это может быть неуместно. Естественно, я пытаюсь использовать опцию сравнения, чтобы показать предстоящие события, прошлые события в разных местах на этом сайте. В другом месте мне действительно нужно передать параметр value массив, который печатает первый и последний день текущего месяца, ограничивая вывод событиями, происходящими в этом месяце.
<?php
query_posts( array(
'post_type' => 'event', // only query events
'meta_key' => 'event_date', // load up the event_date meta
'orderby' => 'meta_value', // sort by the event_date
'order' => 'asc', // ascending, so earlier events first
'posts_per_page' => '2',
'meta_query' => array( // restrict posts based on meta values
'key' => 'event_date', // which meta to query
'value' => date("Y/m/d h:i A"), // value for comparison
'compare' => '>=', // method of comparison
'type' => 'DATE' // datatype, we don't want to compare the string values
) // end meta_query array
) // end array
); // close query_posts call
?>
4 answers
Я закончил работу над тем же самым, и этот пост был очень полезен. Я использовал пользовательские поля, и вот код, который я использовал для создания списка всех событий , превышающих текущую дату. Обратите внимание на дополнительные фильтры на основе таксономии.
<?php // Let's get the data we need to loop through below
$events = new WP_Query(
array(
'post_type' => 'event', // Tell WordPress which post type we want
'orderby' => 'meta_value', // We want to organize the events by date
'meta_key' => 'event-start-date', // Grab the "start date" field created via "More Fields" plugin (stored in YYYY-MM-DD format)
'order' => 'ASC', // ASC is the other option
'posts_per_page' => '-1', // Let's show them all.
'meta_query' => array( // WordPress has all the results, now, return only the events after today's date
array(
'key' => 'event-start-date', // Check the start date field
'value' => date("Y-m-d"), // Set today's date (note the similar format)
'compare' => '>=', // Return the ones greater than today's date
'type' => 'DATE' // Let WordPress know we're working with date
)
),
'tax_query' => array( // Return only concerts (event-types) and events where "songs-of-ascent" is performing
array(
'taxonomy' => 'event-types',
'field' => 'slug',
'terms' => 'concert',
),
array(
'taxonomy' => 'speakers',
'field' => 'slug',
'terms' => 'songs-of-ascent',
)
)
)
);
?>
В первую очередь это во многом зависит от того, как ваша дата хранится в мета-значении. В общем, это хорошая идея хранить даты в MySQL в виде дат/временных меток MySQL.
Временные метки MySQL имеют формат Y-m-d h:i:s
.
Тем не менее, всегда полезно использовать собственные функции изменения даты WP. Таким образом, чтобы получить текущую дату в формате MySQL, используйте current_time('mysql')
.
Чтобы отформатировать дату MySQL для отображения, используйте mysql2date($format, $mysql_date)
.
В этом случае лучше всего отображать дату так, как она настроена в настройках, поэтому используйте $format = get_option('date_format');
.
Чтобы сохранить выбранную пользователем дату, вам придется перекодировать ее в дату MySQL. Для этого самый простой, но не самый безопасный способ - date('Y-m-d h:i:s', $unix_timestamp);
. $unix_timestamp
часто может быть получен с помощью strtotime($user_input)
.
Однако strtotime()
не выполняет проверку на вменяемость самостоятельно, поэтому лучше написать собственную функцию разговора.
Что касается получения диапазона месяцев, вот функция, которую я использую, чтобы получить границы месяца для любой временной метки MySQL:
function get_monthrange($time) {
$ym = date("Y-m", strtotime($time));
$start = $ym."-01";
$ym = explode("-", $ym);
if ($ym[1] == 12) {
$ym[0]++; $ym[1] = 1;
} else {
$ym[1]++;
}
$d = mktime( 0, 0, 0, $ym[1], 1, $ym[0] );
$d -= 86400;
$end = date("Y-m-d", $d);
return array( $start, $end );
}
Если вы хотите получить границы недели, WP уже поставляется с функцией для этого: get_weekstartend($time);
, которая также предоставляет границы в виде массива.
Затем вы можете использовать их в своем аргументе meta_query
, выполнив два отдельных сравнения.
В итоге я остановился на следующем. Я настраиваю поле "момент события" и сравниваю оттуда. спасибо за помощь
<?php
$event_query = new WP_Query(
array(
'post_type' => 'event', // only query events
'meta_key' => 'event-month', // load up the event_date meta
'order_by' => 'event_date',
'order' => 'asc', // ascending, so earlier events first
'meta_query' => array(
array( // restrict posts based on meta values
'key' => 'event-month', // which meta to query
'value' => date("n"), // value for comparison
'compare' => '=', // method of comparison
'type' => 'NUMERIC' // datatype, we don't want to compare the string values
) // meta_query is an array of query ites
) // end meta_query array
) // end array
); // close WP_Query constructor call
?>
<?php while($event_query->have_posts()): $event_query->the_post(); //loop for events ?>
Привет, ниже я публикую свое решение. Где я сохранил дату в формате Y-m-d H:i
(например 2013-07-31 16:45).
- Сортировка по дате начала события.
-
Событие, которое заканчивается после сегодняшнего дня, будет запрашиваться только
meta_query
.date_default_timezone_set('Asia/Calcutta');
Я установил часовой пояс по умолчанию для функции date()
.
$args = array(
'posts_per_page' => 3,
'orderby' => 'meta_value',
'meta_key' => 'event_start_date_time',
'order' => 'ASC',
'post_type' => 'events',
'meta_query' => array(
array(
'key' => 'event_end_date_time',
'value' => date("Y-m-d H:i"),
'compare' => '>=',
'type' => 'DATE'
)
)
);
query_posts( $args );
if( have_posts() ) : while ( have_posts() ) : the_post();