Add Product Schema to WooCommerce
You can use Fluent Snippets to insert the following schema code into your WooCommerce store.
Notes:
- The short description from the product will be used as the schema description. Make sure it contains plain text only—avoid HTML or styling tags.
- The priceValidUntil field is automatically set to 6 months from the current date.
- Always verify the output using Google's Rich Results Test to ensure the structured data is correctly rendered and eligible for rich snippets.
Snippet
// Version 2024-04-28
// For support email info@microbite.com.au
// Bricks - Woo product schema
function update_price_valid_until() {
$currentDate = date('Y-m-d');
$priceValidUntil = get_option('woocommerce_price_valid_until');
if (empty($priceValidUntil) || $currentDate >= $priceValidUntil) {
$priceValidUntil = date('Y-m-d', strtotime('+6 months'));
update_option('woocommerce_price_valid_until', $priceValidUntil);
}
return $priceValidUntil;
}
add_action('wp_footer', 'add_product_structured_data');
function add_product_structured_data() {
if (!function_exists('is_product') || !is_product()) {
return;
}
global $product;
if (!is_object($product)) {
error_log('WP Structured Data Error: $product is not an object');
return;
}
$priceValidUntil = update_price_valid_until();
$imageUrl = get_the_post_thumbnail_url($product->get_id(), 'medium');
if (!$imageUrl) {
error_log('WP Structured Data Error: Failed to get image URL');
}
$imageUrlEscaped = esc_url($imageUrl);
$productNameEscaped = esc_html($product->get_name());
$productDescriptionEscaped = esc_html($product->get_short_description());
$productSkuEscaped = esc_html($product->get_sku());
$productPriceEscaped = esc_js($product->get_price());
$currencyEscaped = esc_attr(get_woocommerce_currency());
$blogNameEscaped = esc_html(get_bloginfo('name'));
$stockStatus = $product->is_in_stock() ? "https://schema.org/InStock" : "https://schema.org/OutOfStock";
$structuredData = [
"@context" => "https://schema.org/",
"@type" => "Product",
"name" => $productNameEscaped,
"image" => $imageUrlEscaped,
"description" => $productDescriptionEscaped,
"mpn" => $productSkuEscaped,
"sku" => $productSkuEscaped,
"offers" => [
"@type" => "Offer",
"priceCurrency" => $currencyEscaped,
"price" => $productPriceEscaped,
"priceValidUntil" => $priceValidUntil,
"itemCondition" => "https://schema.org/NewCondition",
"availability" => $stockStatus,
"seller" => [
"@type" => "Organization",
"name" => $blogNameEscaped
]
]
];
if ($product->get_review_count() > 0) {
$structuredData["aggregateRating"] = [
"@type" => "AggregateRating",
"ratingValue" => esc_attr($product->get_average_rating()),
"reviewCount" => esc_attr($product->get_review_count())
];
}
echo '';
}
?>