跳至正文
Shopify · Google SEO

Shopify 变体与 Offer:一件商品多个规格时结构化数据怎么写

// / / 光算科技

一件商品有五种颜色、四个尺码,页面上该标一个 Offer 还是标一个价格区间?判断标准不在变体数量上,而在于这一页的加购行为到底指向什么:页面一次只能选中一个规格,价格与库存任一时刻只显示一个值,就该用单个 Offer;页面整体以「一件商品、多个可选项」呈现,价格本身就以区间展示,才轮到 AggregateOffer。搞反方向,标注就会与页面自相矛盾。

两种写法各自成立的条件

单 Offer 的写法里,Product 描述整件商品,Offer 描述页面上当前真正可购买的那个规格,价格、币种、库存状态都跟着它走。用这个写法的页面,规格切换通常不换地址,用户和爬虫看到的是同一个产品 URL 上的不同状态。

多规格商品的两种表达:选哪种取决于页面上怎么呈现

选哪种取决于页面上怎么呈现(光算 · 示意图)

AggregateOffer 描述整件商品的价格范围,适合本来就以区间定价呈现的页面,比如页面上写着「19.90 起」,或者规格列表平铺展示、每个规格都标着价。它给出的 lowPrice 与 highPrice 必须覆盖页面上当前所有可售的规格。只要最便宜的那个规格长期缺货,区间就是在描述一个买不到的价,这种事靠肉眼看不出来,需要按规格逐一对一遍。

页面形态合适的写法最容易翻车的地方
单规格可购买页,切换规格不换地址一个 Product + 一个 OfferOffer 里的价格停在默认规格,切到别的规格后不跟着变
整件商品呈现,价格以区间出现一个 Product + AggregateOffer区间两端与页面上真实可售的组合对不上
每个变体都被生成了独立地址每个地址各自一个 Product + Offer变体页里又输出一遍整页区间,两份标注互相矛盾

最麻烦的是把前两种混着用:整页输出区间,页面上某处又输出具体价格。搜索引擎不会替你挑一个,它看到的是同一件事的两组值,结果通常是这些数值被忽略,或者在报告里反复波动。

单 Offer 的核对顺序

不必先读懂模板代码,按页面行为核对更快,也更容易撞见真实问题:

  1. 把规格逐个切换一遍,每切一次就在当前页打开源码,搜索 application/ld+json,看 price、priceCurrency、availability 三个值有没有跟着切换。
  2. 如果三个值从头到尾没变,这份标注基本是模板静态输出的,通常只对应默认规格。这时要么让输出跟着选中规格走,要么在页面和标注上都明确它只描述默认规格;第二种做法在默认规格容易缺货的商品上不能用。
  3. 缺货规格不要把旧价格留着不提。availability 要表达不可购买;如果页面在缺货时不显示价格,标注里也不要继续报一个买不到的价,宁可让这一条标注只覆盖当前可售的规格,也不要让页面上写着缺货、标注里写着有货还有价。
  4. 挑一两个正在促销的规格,确认标注里的价格就是当前实际售价。
  5. 最后确认变体选择逻辑和标注输出用的是同一处数据。主题里常见的情况是规格切换走一套 JavaScript,标注由模板单独渲染,两边各自读了一个字段,改商品数据时只更新了其中一边。

促销价这一步出错最多。Shopify 的价格设置里,原价与划线价是两个字段,前台也分两处显示,把划线价写进 price 字段,等于在最显眼的位置报了买家结账时看不到的价格。Shopify 的产品详细信息文档把产品层与变体层的价格、库存、运费分开说明——加了变体之后,这些值在变体层维护,所以结构化数据里的价格来源应该是变体层的售价,不是产品层用来概览的信息。同一份文档也提到,产品详情页上价格、库存、运费这些区块在加入变体后就不再显示在那一层,这也解释了很多店铺改价后页面与标注对不上的原因。

{
  "@context": "https://schema.org",
  "@type": "Product",
  "name": "示例产品名称",
  "offers": {
    "@type": "Offer",
    "price": "29.90",
    "priceCurrency": "USD",
    "availability": "https://schema.org/InStock",
    "url": "https://example.com/products/example?variant=1001"
  }
}

价格要输出成不带货币符号、不带千分位的纯数字字符串,币种放在 priceCurrency。在 Liquid 里生成这段 JSON 时,过滤器的组合方式取决于主题现有的写法,不要照抄别家主题的写法;改完先在副本主题预览,用结构化数据测试工具确认输出结果,再发布。

价格区间的最小写法与它的硬伤

区间写法看起来省事,实际约束更紧。下面是最小结构,除两个价格端点外都是可选字段,但可选不等于可以乱填。

抽样要覆盖的情况:这几种最容易出现标注矛盾

这几种最容易出现标注矛盾(光算 · 示意图)

{
  "@context": "https://schema.org",
  "@type": "Product",
  "name": "示例产品名称",
  "offers": {
    "@type": "AggregateOffer",
    "priceCurrency": "USD",
    "lowPrice": "19.90",
    "highPrice": "34.50"
  }
}

区间的硬伤在于它对库存变化特别敏感。促销结束、某个规格下架、某个规格补货,两个端点都可能要跟着改;如果标注是模板静态写死的,你根本不会知道它已经不对了。所以选区间写法之前先问一句:这个区间是谁在维护,改动的触发点在哪里。答不上来,就用单 Offer。

先分清是数据的问题还是标注的问题

核对之前有个前提,不然后面所有排查都在白费力气。页面本身显示的库存与价格就不对,那是后台数据的问题,去改标注没有意义,先去后台把产品、变体、市场的价格与库存理顺。反过来,页面显示的数值正确,源码里的数字不对,才轮到改模板或负责输出的插件。分不清这两边,最常见的结果是后台被改坏,标注里的问题还在原地。

判断方法很直接:用同一个浏览器窗口,左边开着前台页面,右边开着该页的源码,逐个规格对。凡是页面上就对不上的,先停,去后台;页面对得上、源码对不上的,继续往下看模板。

变体有独立地址时,先决定谁代表这件商品

有些主题或应用会为每个变体生成可独立访问的地址。这时候每个地址上的标注都只能描述它自己那一个规格,否则等于两个地址各自声明自己是完整商品,内容却一样。Google 关于 URL 规范化的说明讲得很明确:页面重复或高度相似时,由 Google 聚类并挑出代表地址,rel="canonical" 这类标注是提示而不是规则。也就是说,最终哪个地址被当成代表,你说了不算;你能控制的是每个地址上的标注与页面内容是否自洽,以及链接、sitemap 里出现的到底是哪一种地址。

顺带把 sitemap 也对一遍。Shopify 的 sitemap 由平台自动生成,官方的 sitemap 文档说明它收录的是产品、主产品图、页面、集合和博客文章,并会随新增内容自动更新。这份结构里没有「每个变体一条」的承诺,所以不要假设你为变体造的独立地址一定会被 sitemap 带上;这类地址能不能被发现,取决于站内链接和主题里的链接输出。sitemap 的三层结构与常见报错可以接着看Shopify sitemap 结构解析

如果变体之间的差异只是颜色这类外观变化,页面没有独立内容,也没有人按「某颜色 某尺码」这样的词搜索,那么为每个变体造一套独立标注的收益很低,维护成本却随规格数量翻倍。这类情况优先让规格保持在同一个产品 URL 上表达,具体取舍在变体是否要做独立页面那一篇里有更细的判断。

抽样核对:缺货、促销、多币种

标注的正确性没法一次性验完,只能抽样,而且每次改完产品数据都要重跑。下面三项在同时开了多个市场的店铺里优先做。

检查项怎么查通过标准
缺货规格把某个规格库存改成 0,看前台源码availability 标注为不可购买,价格不残留旧值
促销价同一规格同时看前台显示价与源码 price两处一致,划线价没有出现在 price 里
多市场币种用目标市场的前台地址打开同一产品priceCurrency 与页面显示的币种一致,数值等于该市场实际售价

币种这一项最容易想当然。开了多市场之后,同一个产品地址在不同市场显示不同货币,按汇率心算出来的数字不等于当地售价。核对时不要用主站地址加换算,要用目标市场的实际前台地址,并以后台的市场与货币设置为准。价格与币种如何避免制造重复页面,币种与价格展示对收录的影响那篇可以接着看。

这几种情况不值得投入

标注不会自动带来展示。Google 的产品结构化数据文档把各类结果增强项写得很保守:是否显示由各个搜索体验自行决定,还会随时间变化,文档的建议是把可用的产品信息尽量补全,而不是去猜哪个体验会用到。既然如此,把精力放在让数字准确,比堆字段划算。

也不值得为一个只有两三个规格、库存长期稳定的产品反复折腾表达方式。规格少、页面简单时,单 Offer 写对了就够用,同样的时间投到产品描述与集合页结构上回报更大。标注漂移需要日常发现,不是一次性工程,整页字段怎么核、报告里怎么看出问题,分别写在产品结构化数据核对富媒体结果核对里。

最后是归属问题。如果规格与市场的组合已经多到手改不过来,先要解决的是页面结构而不是标注:哪些规格留在同一页、哪些值得独立成页、地址与内链怎么安排,这些决定做完,标注只是照实描述。反过来,如果规格不多、页面结构清楚,只是标注没人维护,那就不需要重做结构,定一个每次改价的复核动作更实际。这类站点结构规划属于谷歌 SEO 的常规工作范围,加一段 JSON 解决不了。