Вопрос или проблема
Я выполняю следующий запрос, пытаясь получить данные и сопутствующие метаданные большого количества публикаций:
SELECT wp_posts.post_title, wp_posts.post_date,
wp_posts.ID, wp_postmeta.post_id, wp_postmeta.meta_key
FROM wp_postmeta
INNER JOIN wp_posts
ON wp_postmeta.post_id=wp_posts.id
WHERE wp_posts.post_status="publish"
LIMIT 5
И это возвращает следующее:
Массив
(
[0] => stdClass Объект
(
[post_title] => Привет, мир!
[post_date] => 2015-11-11 08:44:54
[ID] => 1
[post_id] => 1
[meta_key] => _edit_lock
)
[1] => stdClass Объект
(
[post_title] => Главная
[post_date] => 2015-11-11 08:44:54
[ID] => 2
[post_id] => 2
[meta_key] => _wp_page_template
)
[2] => stdClass Объект
(
[post_title] => Главная
[post_date] => 2015-11-11 08:44:54
[ID] => 2
[post_id] => 2
[meta_key] => _edit_last
)
...
Но теперь я понимаю, что мне нужен гораздо более сложный запрос, так как то, что я хотел бы, это что-то вроде следующего:
Массив
(
[0] => stdClass Объект
(
[post_title] => Привет, мир!
[post_date] => 2015-11-11 08:44:54
[ID] => 1
[post_id] => 1
[meta] => массив(
'_wp_page_template' => 'home.php',
'_edit_last' => 2015-11-11 08:44:54,
)
)
[1] => stdClass Объект
(
[post_title] => Главная
[post_date] => 2015-11-11 08:44:54
[ID] => 2
[post_id] => 2
[meta] => массив(
'_wp_page_template' => 'home.php',
'_edit_last' => 2015-11-11 08:44:54,
)
)
[2] => stdClass Объект
(
[post_title] => О нас
[post_date] => 2015-11-11 08:44:54
[ID] => 3
[post_id] => 3
[meta] => массив(
'_wp_page_template' => 'home.php',
'_edit_last' => 2015-11-11 08:44:54,
)
)
Это действительно просто.
get_post_meta($postid);
Это вернет все значения примерно в том же синтаксисе.
В более рабочем цикле:
<?php
$custom = new WP_Query(array("posts_per_page" => -1))
if( $custom->have_posts() ) {
while ( $custom->have_posts() ) {
the_post();
$data = get_post_meta(get_the_ID());
}
} else {
/* Записей не найдено */
}
?>
Для всех, кто наткнется на это.. Я решил эту задачу, сделав следующее:
(адаптировано под ваш код)
SELECT wp_posts.post_title, wp_posts.post_date,
wp_posts.ID, wp_postmeta.post_id, wp_postmeta.meta_key,
GROUP_CONCAT(wp_postmeta.meta_key SEPARATOR ':') AS meta_keys
FROM wp_postmeta
INNER JOIN wp_posts
ON wp_postmeta.post_id=wp_posts.id
WHERE wp_posts.post_status="publish"
GROUP BY wp_postmeta.post_id
LIMIT 5
Сделав GROUP_CONCAT(wp_postmeta.meta_key SEPARATOR ':') AS meta_keys
и GROUP BY wp_postmeta.post_id
, создается результат meta_keys
, по которому вы затем в PHP можете разделить по :
$meta_keys = explode(':', $item->meta_keys);
Ответ или решение
Чтобы извлечь все метаданные, связанные с каждой публикацией в WordPress, вам необходимо оптимизировать ваш SQL-запрос и применять определенные техники для обработки этих данных. Давайте разберемся поэтапно.
Постановка задачи
Ваша задача состоит в том, чтобы получить данные о произвольном числе опубликованных записей и все связанные с ними метаданные в удобном для использования формате. Начальный SQL-запрос уже предоставляет базовую информацию, однако его результаты нужно легко структурировать.
Начальный запрос
Вот ваш исходный запрос:
SELECT wp_posts.post_title, wp_posts.post_date,
wp_posts.ID, wp_postmeta.post_id, wp_postmeta.meta_key
FROM wp_postmeta
INNER JOIN wp_posts
ON wp_postmeta.post_id=wp_posts.ID
WHERE wp_posts.post_status="publish"
LIMIT 5
Оптимизация запроса
Используя оператор GROUP_CONCAT()
, вы сможете объединить все ключи метаданных в одну строку для каждой публикации. Вот как может выглядеть оптимизированный SQL-запрос:
SELECT wp_posts.post_title, wp_posts.post_date,
wp_posts.ID,
GROUP_CONCAT(CONCAT(wp_postmeta.meta_key, ':', wp_postmeta.meta_value) SEPARATOR ',') AS meta_data
FROM wp_postmeta
INNER JOIN wp_posts
ON wp_postmeta.post_id = wp_posts.ID
WHERE wp_posts.post_status = "publish"
GROUP BY wp_posts.ID
LIMIT 5
Объяснение запроса
-
GROUP_CONCAT(): Эта функция объединяет значения в одну строку, отделяя их запятой. Каждый элемент имеет формат
meta_key:meta_value
, что упрощает дальнейшую обработку. -
GROUP BY: Благодаря группировке по
wp_posts.ID
, вы гарантируете, что для каждой публикации будет возвращена только одна строка с её заголовком, датой и метаданными.
Использование данных в PHP
Теперь после выполнения этого запроса вы получите более удобную структуру данных. В вашем PHP коде, вы можете обработать этот результат следующим образом:
$results = $wpdb->get_results($sql);
foreach ($results as $item) {
$meta_data_pairs = explode(',', $item->meta_data);
$meta = [];
foreach ($meta_data_pairs as $pair) {
list($key, $value) = explode(':', $pair);
$meta[$key] = $value;
}
$post_info = [
'post_title' => $item->post_title,
'post_date' => $item->post_date,
'ID' => $item->ID,
'meta' => $meta,
];
// Теперь $post_info содержит нужные данные
print_r($post_info);
}
Заключение
Этот подход позволяет вам объединить метаданные для каждой записи в одну структуру, что значительно упрощает дальнейшую обработку данных. Используя функцию GROUP_CONCAT()
, вы можете легко манипулировать множеством метаданных и получать необходимую информацию в компактном формате.
Следуя этому способу, вы не только оптимизируете свои запросы к базе данных, но и обретете большинство необходимых вам данных в очень удобном виде.