На страницах категорий WooCommerce я хочу получить существующие результаты запроса и использовать их для заполнения данных схемы для «OfferCatalog».
Это самая близкая функция, которую я могу найти к тому, что мне нужно:
/**
* Add structured data to the WooCommerce shop page.
*
* @param array $markup The structured data markup.
* @param WP_Query $query The current WP_Query object.
* @return array The modified structured data markup.
*/
function add_structured_data_to_shop_page( $markup, $query ) {
if ( is_shop() || is_product_category() || is_product_tag() ) {
$markup['@type'] = 'CollectionPage';
$markup['mainEntity']['@type'] = 'OfferCatalog';
$markup['mainEntity']['itemListElement'] = array();
$products = $query->get_posts();
foreach ( $products as $product ) {
$markup['mainEntity']['itemListElement'][] = array(
'@type' => 'Product',
'name' => get_the_title( $product->ID ),
'url' => get_permalink( $product->ID ),
'image' => get_the_post_thumbnail_url( $product->ID, 'full' ),
'description' => get_the_excerpt( $product->ID ),
'offers' => array(
'@type' => 'Offer',
'price' => get_post_meta( $product->ID, '_price', true ),
'priceCurrency' => get_woocommerce_currency(),
'availability' => 'https://schema.org/InStock', // Adjust as needed
),
);
}
}
return $markup;
}
add_filter( 'woocommerce_structured_data', 'add_structured_data_to_shop_page', 10, 2 );
Но ничего не выводится. Я подозреваю, что woocommerce_structured_data отключен или удален со страниц категорий. Я пробовал разные хуки, но все равно ничего не вижу.
Как я могу заставить это работать (не повторяя запрос к базе данных)?






Обновлять
Вы не можете использовать существующие фильтры, связанные с WooCommerce, поскольку вы добавляете новый структурированный тип данных.
Что вы можете сделать, так это добавить в нижний колонтитул свои собственные структурированные данные, например:
/**
* Add structured data to the WooCommerce archive pages.
*/
add_action( 'wp_footer', 'output_wc_archive_pages_structured_data', 10 );
function output_wc_archive_pages_structured_data() {
// Only on WooCommerce archives
if ( is_shop() || is_product_category() || is_product_tag() ) {
global $wp_query; // Get the current WP_Query object
$markup_data = array(); // Initializing
$markup_data['@context'] = 'https://schema.org/';
$markup_data['@type'] = 'CollectionPage';
$markup_data['mainEntity']['@type'] = 'OfferCatalog';
$markup_data['mainEntity']['itemListElement'] = array(); // Initializing
$product_posts = $wp_query->get_posts(); // Get the posts from the current query
// Loop through product posts
foreach ( $product_posts as $product_post ) {
$product_id = $product_post->ID;
$markup_data['mainEntity']['itemListElement'][] = array(
'@type' => 'Product',
'name' => wp_kses_post( get_the_title( $product_id ) ),
'url' => esc_url( get_permalink( $product_id ) ),
'image' => esc_url( get_the_post_thumbnail_url( $product_id, 'full' ) ),
'description' => wp_strip_all_tags( get_the_excerpt( $product_id ) ),
'offers' => array(
'@type' => 'Offer',
'price' => wc_format_decimal( get_post_meta( $product_id, '_price', true ), wc_get_price_decimals() ),
'priceCurrency' => esc_attr( get_woocommerce_currency() ),
'availability' => $markup_data['@context'] . esc_attr( get_post_meta( $product_id, '_stock_status', true ) ),
),
);
}
echo '<script type = "application/ld+json">' . wc_esc_json( wp_json_encode( $markup_data ), true ) . '</script>';
}
}
Код находится в файле function.php вашей дочерней темы (или в плагине). Протестировано и работает.
Это работает отлично. Спасибо. Всего один вопрос: зачем вам wp_kses_post()? get_the_title($product_id) должен возвращать простой текст без каких-либо тегов, которые необходимо удалить.
@Mesmer7 Для отдельных страниц продукта в соответствующем коде структурированных данных ('@type' => 'Product') WooCommerce использует wp_kses_post() в кратком описании продукта: см. метод WC_Structured_Data::generate_product_data() исходный код .
Я попробовал оба метода. Не выводите нужные данные схемы. Но с помощью второго метода я ввел команду «эхо» и проверил, что функция вызывается.