Perché lo schema Product impatta Shopping
Google incrocia segnali: pagina prodotto + feed + markup. Non li valuta in isolamento. Se il markup dichiara un prezzo diverso dal visibile, o uno stock diverso dal feed, il sistema non "sceglie il più comodo": rileva l'inconsistenza e aumenta la probabilità di blocchi e disapprovazioni.
Il problema è spesso sistemico, non puntuale: un plugin aggiornato, una cache non purgata, un currency switcher lato client. Il risultato è markup che "sembra giusto" ma non lo è, e Google lo vede ogni volta che esegue il crawl.
Campi essenziali: cosa serve davvero
La parte più critica è Offer, perché contiene
price, priceCurrency e
availability. Con varianti e prezzi dinamici,
qui nasce la maggior parte dei mismatch.
| Campo | Obbligatorio? | Errore tipico | Fix rapido |
|---|---|---|---|
@type: Product |
Sì | Duplicato (2 Product nella pagina) | Disattiva una fonte (tema/plugin/app) |
offers.price + priceCurrency |
Sì | Prezzo markup ≠ prezzo visibile | Allinea la fonte del prezzo (server-side o URL per variante) |
offers.availability |
Sì | InStock in markup, OutOfStock in pagina | Sincronizza stock reale + purge cache/CDN |
brand |
Consigliato | Brand mancante o generico | Brand coerente tra pagina, markup e feed |
sku, gtin, mpn |
Quando applicabile | Valori inconsistenti tra varianti | SKU per variante + GTIN corretto (se presente) |
aggregateRating, review
o prezzi promozionali restino coerenti nel tempo, non inserirli.
Meglio un markup "pulito" che uno che genera errori intermittenti.
Markup duplicato: il problema #1
Due blocchi JSON-LD Product nella stessa pagina sono
la causa più comune di mismatch. Spesso uno dei due resta "indietro" —
cache non purgata, snippet legacy, plugin non aggiornato —
e dichiara price o availability
non aggiornati. Google vede entrambi e rileva l'incoerenza.
Da dove arrivano i duplicati
- Plugin SEO + plugin schema + WooCommerce che generano tutti JSON-LD in modo indipendente.
- Tema che include schema + snippet custom in header o footer (spesso dimenticato dopo una migrazione).
- Shopify: app SEO + schema del tema + app per varianti o currency switcher.
- Snippet "legacy" lasciati da sviluppatori precedenti nel codice del tema o in tag GTM.
"@type":"Product" o usa
Rich Results Test. Conta le occorrenze: deve essercene esattamente 1 "principale".
Prezzo/stock incoerenti: cause tipiche
Il mismatch non è quasi mai un errore "intenzionale": nasce da un disallineamento tra il momento in cui il markup viene generato e quello in cui l'utente (o il crawler) vede la pagina. I pattern ricorrenti sono quattro.
- Prezzi via JavaScript (varianti, sconti dinamici, bundle, upsell): il JSON-LD viene stampato server-side con il prezzo "base", ma l'utente vede un prezzo diverso dopo l'esecuzione del JS.
- Cache / CDN: il markup viene aggiornato (es. dopo una promo), ma la pagina cached continua a servire il prezzo precedente — o viceversa.
-
Multi-valuta: il currency switcher cambia la UI lato client
ma non aggiorna
priceCurrencynel JSON-LD. - Preorder / esaurimento scorte gestiti da app/webhook lato magazzino ma non sincronizzati con il markup in modo affidabile.
- Apri la pagina in incognito (nessuna cache browser).
- Confronta prezzo e stock visibili con il JSON-LD (view-source o DevTools → tab "Elements" → cerca
application/ld+json). - Cambia variante: il markup
Offersi aggiorna in modo coerente? - Purge cache applicativa + CDN, poi ripeti — sia da desktop che da mobile.
Varianti: item_group_id, URL e Offer
Con prodotti in varianti (taglia, colore, capacità), la coerenza del markup dipende dall'architettura URL che hai scelto. Hai due strade principali.
- Offer stabile per URL — meno rischio di mismatch
- Soluzione più robusta per Shopping e Merchant Center
-
item_group_idnel feed aggrega le varianti
- JSON-LD deve aggiornarsi in modo affidabile via JS
- Rischio maggiore se il crawler non esegue JS correttamente
- Offer può restare "bloccata" sulla variante default
item_group_id per collegare le varianti allo stesso prodotto padre.
Multi-valuta e geo-pricing: come non rompersi
Currency switcher e geo-pricing creano mismatch quando cambiano la UI ma non il JSON-LD. Il risultato pratico: l'utente (e il crawler) vede EUR 999 in pagina, ma il markup dichiara USD 999 o un EUR con valore diverso.
-
Se la valuta dipende dalla geolocalizzazione, assicurati che
priceCurrencysegua la stessa logica server-side — non solo la UI. - Se i prezzi cambiano lato client (switcher JS), valuta URL separati per mercato o rendering server-side per garantire il prezzo finale nel markup.
- Evita "prezzi stimati" in UI e "prezzi finali" nel markup: devono combaciare nello stesso momento, non in media.
-
Con Shopify e app multi-currency: verifica quale app gestisce il JSON-LD
e se aggiorna
priceCurrencyo solo la UI visibile.
Cache/CDN: il nemico silenzioso
Molti siti aggiornano UI e database (prezzo/stock) ma continuano a servire un JSON-LD cache-ato con i valori precedenti. Oppure l'opposto: il markup viene rigenerato, ma la pagina cached è ancora quella vecchia. In entrambi i casi Google vede un'incoerenza sistematica.
- Dopo ogni fix di prezzo, disponibilità o descrizione: purge cache applicativa + CDN + object cache (se presente).
- Testa in incognito e da una rete diversa (es. hotspot mobile) per evitare cache "invisibili" legate alla tua connessione o browser.
- Per pagine con varianti: testa 2–3 varianti specifiche, non solo quella default — spesso la cache è granulare per URL parametrica.
- Se usi SSG (es. Next.js static, Gatsby): verifica che le rebuild coprano anche le pagine prodotto, non solo home e categorie.
WordPress/Woo/Shopify: conflitti frequenti
Le piattaforme più diffuse hanno pattern di conflitto ben definiti. Ecco quelli che generano più ticket di supporto e disapprovazioni.
- Yoast / RankMath + plugin schema: duplicazione Product con Offer discordanti.
- Tema con schema + Woo schema nativo: doppia Offer, spesso con prezzi diversi.
- Plugin sconti / price rules: aggiorna solo la UI, non il JSON-LD.
- WP Rocket / LiteSpeed cache: serve markup vecchio dopo update prodotto.
- App SEO / structured data + theme JSON-LD: due Product in pagina.
- Currency switcher: valuta UI ≠ valuta nel markup (
priceCurrencynon aggiornato). - Varianti: Offer resta fissa sulla variante default anche dopo il cambio.
- Metafields custom: spesso sovrascrivono il JSON-LD del tema in modo parziale.
Snippet JSON-LD "compliance-first" (robusto)
Questo è lo snippet minimale ma stabile che raccomandiamo come punto di partenza. Aggiungi proprietà aggiuntive solo se sei certo che restino coerenti dopo ogni aggiornamento di tema, plugin o app.
{
"@context": "https://schema.org",
"@type": "Product",
"name": "Brand Modello — Variante specifica",
"image": [
"https://example.com/images/prodotto-fronte.jpg",
"https://example.com/images/prodotto-lato.jpg"
],
"sku": "SKU-VARIANTE-001",
"gtin": "0000000000000",
"brand": {
"@type": "Brand",
"name": "NomeBrand"
},
"offers": {
"@type": "Offer",
"url": "https://example.com/prodotto?variant=001",
"priceCurrency": "EUR",
"price": "1299.00",
"priceValidUntil": "2025-12-31",
"availability": "https://schema.org/InStock",
"itemCondition": "https://schema.org/NewCondition",
"seller": {
"@type": "Organization",
"name": "Nome Negozio"
}
}
}
price e JS:
questo snippet è corretto solo se il valore stampato server-side coincide
con il prezzo visibile all'utente, anche dopo cambio variante e applicazione di sconti.
Se c'è una discrepanza anche minima, allinea prima la fonte del prezzo.
ratingValue statico che non rispecchia le recensioni attuali è un errore.
Checklist tecnica (fix rapidi)
Usa questa checklist dopo ogni modifica significativa al sito (aggiornamento tema, nuovo plugin, cambio listino, integrazione app).
@type.*Product.price, priceCurrency, availability devono essere presenti e corretti.Validazione e monitoraggio nel tempo
Dopo i fix, la parte difficile è non romperlo al prossimo aggiornamento di tema, plugin o app. La coerenza non è uno stato statico: è un processo.
- Definisci un set fisso di 10–20 prodotti campione (varianti incluse, diverse fasce di prezzo, diversi stati stock) e testali sempre quelli.
- Dopo ogni update SEO plugin / theme / checkout: re-audit rapido sull'intero set.
- Se introduci una nuova app o plugin che tocca il markup: verifica duplicazioni prima del deploy in produzione.
- Monitora Search Console → Miglioramenti → Dati strutturati: gli errori segnalati lì sono quasi sempre reali.
- Se usi Google Ads: incrocia le disapprovazioni con le date di aggiornamento tema/plugin — spesso coincidono.
Vuoi verificare automaticamente se lo schema Product è coerente?
Registrati e genera un report: trust signals, policy, coerenza prezzo/stock e controlli schema.org Product — tutto in un unico audit.