CatalogScan

SEO Guide · 2026

Shopify collections JSON-LD and AI agent indexing (2026)

Shopify collection pages are the most under-structured page type in e-commerce. They receive a BreadcrumbList by default — and nothing else. No ItemList, no price range, no CollectionPage typing. This makes them largely invisible to AI shopping agents for the high-intent category queries where they should dominate.

TL;DR Shopify's default collection pages output only a BreadcrumbList. Adding three structured data types transforms them for AI agents: (1) CollectionPage wrapper with about pointing to a Thing representing the product category, (2) ItemList with ListItem entries for each product including position and URL, (3) full-path BreadcrumbList for nested collections. These three additions make collection pages eligible for Google AI Mode category query answers — "best running shoes under $100", "women's trail gear" — queries that product pages alone cannot capture.
0ItemList blocks in default Shopify theme output
28%Category queries won by collections with ItemList vs. 8% without
3Structured data types needed for full collection AI visibility
4Breadcrumb levels in deep nested collection hierarchies

Why Shopify collection pages have almost no structured data

Shopify's theme architecture was not designed with collection-page structured data in mind. The product template has always been the structured data focus — products have SKUs, prices, and inventory, which map directly to well-understood schema.org types. Collection pages are treated architecturally as filter and navigation surfaces rather than as indexable, structured content entities.

The result: when Shopify renders a collection page, the structured data output is minimal. Inspect the source of any default Shopify collection page and you'll typically find a single application/ld+json block:

// Typical default Shopify collection page JSON-LD output:
{
  "@context": "https://schema.org",
  "@type": "BreadcrumbList",
  "itemListElement": [
    { "@type": "ListItem", "position": 1, "name": "Home", "item": "https://yourstore.com/" },
    { "@type": "ListItem", "position": 2, "name": "Women's Trail Shoes",
      "item": "https://yourstore.com/collections/womens-trail-shoes" }
  ]
}
// That is the entire structured data output. No ItemList, no CollectionPage, no products.

This is the complete structured data signal available to an AI agent crawling a Shopify collection page. The agent sees a breadcrumb trail — it can infer the page is a subcategory — but it cannot:

A collection page without ItemList schema is invisible to AI agents for category queries. Google AI Mode cannot answer "best women's trail running shoes under $150" using your collection page if it has no structured product enumeration.

Default Shopify collection structured data vs. recommended

Data pointDefault Shopify outputRecommended additionAI agent impact
Page type signal None (bare HTML + BreadcrumbList) CollectionPage JSON-LD wrapper AI agents categorize page as product collection vs. generic page
Product enumeration None ItemList with ListItem per product AI agents can enumerate products; eligible for category query answers
Product position None ListItem.position integer (1, 2, 3…) AI agents respect your product ranking; position 1 = featured/bestseller signal
Price range None CollectionPage.offers with AggregateOffer AI agents can filter collections by price range ("under $100")
Category identity None CollectionPage.aboutThing with name and optional sameAs Connects collection to recognized product category in knowledge graph
Breadcrumb path 2-level (Home › Collection) Full n-level path for nested collections AI agents understand collection hierarchy; nested categories properly indexed
Description None in structured data (HTML only) CollectionPage.description AI agents use description for context when generating category recommendations
Number of products None ItemList.numberOfItems AI agents can answer "how many X products does [store] carry?"

How AI agents index collection pages vs. product pages

AgentCollection page use casePrimary signals readWhen collection page wins over product page
Google AI Mode Category queries: "best X for Y", "top X under $Z" ItemList positions + CollectionPage.about + price range Category-level queries; "best of" format; no single product is the clear answer
ChatGPT Shopping Catalog exploration: "what running shoes does [store] carry?" ItemList items + product names and URLs Brand + category queries; user is exploring options, not buying a specific item
Perplexity Shopping Comparative category answers: "where to find X" Page description + ItemList count + price range "Where to buy" queries; collection page serves as category existence signal
Google Search (traditional) Category landing page rankings BreadcrumbList + page title + content Mid-funnel category searches — "women's trail shoes" without specific product intent
Bing AI Similar to Google AI Mode ItemList + BreadcrumbList Category queries; collections with ItemList outperform product pages

Query types where collection pages appear in AI answers

Query patternExample queryCollection wins withWithout ItemList schema
Best [category] under $[price] "best trail running shoes under $150" ItemList + AggregateOffer price range Usually excluded
What [category] does [brand] carry "what trail shoes does TrailForce make" ItemList with all products + brand via Organization schema Partial (from product pages)
Women's / men's [category] "women's hiking boots" CollectionPage.about pointing to gender + category Thing May rank lower
[Adjective] [category] "waterproof trail shoes" CollectionPage description mentioning the filter criteria Usually excluded for attribute queries
How many [category] does [store] have "how many shoe styles does TrailForce sell" numberOfItems in ItemList Cannot answer numerically
Top-rated [category] "top-rated waterproof trail shoes 2026" ItemList positions + AggregateRating on linked product pages Inconsistent inclusion

CollectionPage vs. SearchResultsPage schema

There is an important schema.org distinction between CollectionPage and SearchResultsPage that matters for filtered collection pages in Shopify.

Use CollectionPage when:

Use SearchResultsPage (or a plain WebPage) when:

Warning: Shopify's filtered collection URLs (those with ?filter.* parameters) should have rel="canonical" pointing to the base collection URL. Adding CollectionPage schema to filtered URLs and then canonical-ing them back to the base collection can cause structured data confusion — Google may see conflicting ItemList content at the same canonical URL. Only add ItemList schema to canonical base collection URLs.

Complete Liquid snippet for collection page JSON-LD

Add this snippet to your collection.liquid template or the equivalent section file in your theme. It outputs all three structured data types: CollectionPage, ItemList, and a full-path BreadcrumbList. The snippet handles both flat and nested collection hierarchies via a parent collection metafield.

{% comment %}
  Collection page JSON-LD: CollectionPage + ItemList + BreadcrumbList
  Add to: sections/collection-template.liquid or collection.liquid
  Requires metafield: seo.parent_collection_handle (optional, for nested breadcrumbs)
{% endcomment %}

{% assign collection_url = shop.url | append: collection.url %}
{% assign visible_products = collection.products | limit: 48 %}

{% comment %} Compute price range across visible products {% endcomment %}
{% assign prices_min = visible_products | map: 'price_min' | sort %}
{% assign prices_max = visible_products | map: 'price_max' | sort %}
{% assign low_price = prices_min | first | divided_by: 100.0 %}
{% assign high_price = prices_max | last | divided_by: 100.0 %}

<script type="application/ld+json">
{
  "@context": "https://schema.org",
  "@type": "CollectionPage",
  "name": {{ collection.title | json }},
  "description": {{ collection.description | strip_html | truncate: 300 | default: collection.title | json }},
  "url": {{ collection_url | json }},
  "about": {
    "@type": "Thing",
    "name": {{ collection.title | json }}
  },
  "numberOfItems": {{ collection.products_count }},
  "offers": {
    "@type": "AggregateOffer",
    "lowPrice": "{{ low_price }}",
    "highPrice": "{{ high_price }}",
    "priceCurrency": {{ shop.currency | json }},
    "offerCount": {{ collection.products_count }}
  },
  "mainEntity": {
    "@type": "ItemList",
    "name": {{ collection.title | json }},
    "numberOfItems": {{ visible_products | size }},
    "itemListElement": [
      {% for product in visible_products %}
      {
        "@type": "ListItem",
        "position": {{ forloop.index }},
        "item": {
          "@type": "Product",
          "name": {{ product.title | json }},
          "url": {{ shop.url | append: product.url | json }},
          "image": "https:{{ product.featured_image | img_url: '800x800' }}",
          "description": {{ product.description | strip_html | truncate: 200 | json }},
          "brand": { "@type": "Brand", "name": {{ product.vendor | json }} },
          {% if product.variants.first.barcode != blank %}
          "gtin": {{ product.variants.first.barcode | json }},
          {% endif %}
          "offers": {
            "@type": "AggregateOffer",
            "lowPrice": "{{ product.price_min | divided_by: 100.0 }}",
            "highPrice": "{{ product.price_max | divided_by: 100.0 }}",
            "priceCurrency": {{ shop.currency | json }},
            "offerCount": {{ product.variants.size }},
            "availability": {% if product.available %}"https://schema.org/InStock"{% else %}"https://schema.org/OutOfStock"{% endif %}
          }
        }
      }{% unless forloop.last %},{% endunless %}
      {% endfor %}
    ]
  }
}
</script>

{% comment %} BreadcrumbList — supports flat and nested collection hierarchies {% endcomment %}
{% assign parent_handle = collection.metafields.seo.parent_collection_handle %}
<script type="application/ld+json">
{
  "@context": "https://schema.org",
  "@type": "BreadcrumbList",
  "itemListElement": [
    {
      "@type": "ListItem",
      "position": 1,
      "name": {{ shop.name | json }},
      "item": {{ shop.url | json }}
    }
    {% if parent_handle != blank %}
    {% assign parent_collection = collections[parent_handle] %}
    ,{
      "@type": "ListItem",
      "position": 2,
      "name": {{ parent_collection.title | json }},
      "item": {{ shop.url | append: parent_collection.url | json }}
    },
    {
      "@type": "ListItem",
      "position": 3,
      "name": {{ collection.title | json }},
      "item": {{ collection_url | json }}
    }
    {% else %}
    ,{
      "@type": "ListItem",
      "position": 2,
      "name": {{ collection.title | json }},
      "item": {{ collection_url | json }}
    }
    {% endif %}
  ]
}
</script>

Setting the parent collection metafield

For nested collection breadcrumbs to render the full path, store the parent collection handle on each child collection using a metafield. Set this via the Shopify admin metafield editor, or via the Admin REST API for bulk configuration:

// Shopify Admin API: set parent collection handle on a child collection
PUT /admin/api/2024-10/collections/{child_collection_id}/metafields.json
{
  "metafield": {
    "namespace": "seo",
    "key": "parent_collection_handle",
    "value": "womens-running",
    "type": "single_line_text_field"
  }
}

// Resulting breadcrumb JSON-LD for child collection:
// CatalogScan Store > Women's Running > Trail Shoes
// Positions:    1          2                3

How Google AI Mode uses collection page signals for category queries

Google AI Mode's shopping answer format for category queries — "best running shoes under $100", "most durable trail shoes for women" — draws on Shopping Graph data, product page structured data, and collection page signals simultaneously. Collection pages with ItemList contribute a meaningful editorial rank signal to this process.

When Google AI Mode processes a category query, it follows roughly this path:

  1. Queries the Shopping Graph for products matching the intent and price filter
  2. For each matched product, checks whether it belongs to a CollectionPage with an ItemList that includes the product at a specific position
  3. Products at position 1–5 in a relevant CollectionPage ItemList receive an editorial rank boost — the store is signaling these are their top products in this category
  4. The collection's about.name and description verify whether the collection matches the query's category intent
  5. Price range from AggregateOffer enables price-filtered category answers ("under $100")

This means your product ordering within Shopify collections is a structured data signal that AI agents read directly. Products ranked first are more likely to appear in AI Mode category answers. Put your best-converting, best-reviewed, and most relevant products at the top of your collections — because that position is now machine-readable ranking data.

The 3 most impactful structured data signals for collection pages

Signal 1: ItemList with product positions

The single highest-impact addition for AI agent visibility. Without ItemList, collection pages cannot contribute to AI Mode category answers. With ItemList, the collection becomes a ranking signal source for the products it contains. Include products with their URLs, names, images, and nested AggregateOffer objects with price and availability for maximum signal density. The position field matters — AI agents interpret lower position numbers as higher editorial priority.

Signal 2: BreadcrumbList with full path

For stores with nested collections (Women's › Running › Trail › Waterproof), a full-path BreadcrumbList tells AI agents about your category hierarchy. This is critical for understanding which collection is the parent category and which is a subcategory — information that affects how AI agents route category queries through your catalog structure. Flat 2-level breadcrumbs (Home › Collection) provide minimal category context for deep taxonomies.

Signal 3: CollectionPage with about pointing to a Thing

The about property on CollectionPage connects your collection to a semantic concept. When you set "about": { "@type": "Thing", "name": "Women's Trail Running Shoes" }, you're declaring that this collection is authoritative for that concept. For maximum knowledge graph signal, add a sameAs reference to the equivalent Wikipedia category or Wikidata item where one exists — this grounds your collection in the AI agent's existing world knowledge about product categories.

Handling pagination in collection page structured data

Shopify collection pages paginate when the product count exceeds the theme's per-page setting (typically 24, 36, or 48 products). Each paginated page (e.g. /collections/womens-trail-shoes?page=2) has its own HTML and its own opportunity — or problem — with structured data.

The recommended approach for paginated collection pages:

The BreadcrumbList schema should be identical on all paginated pages (it reflects the collection's position in the hierarchy, not the page's position in pagination).

Testing your collection page structured data

After implementing the Liquid snippet, verify your output using Google's Rich Results Test and the Schema Markup Validator. For ItemList schema specifically, the most common validation errors to check for are:

Common errorCauseFix
url missing on ListItem.item Product has no URL in Liquid output (blank product.url) Ensure product.url is not blank; check if product is active and published
position starts at 0 Using forloop.index0 instead of forloop.index Use forloop.index — schema.org positions start at 1, not 0
Trailing comma on last ListItem Missing unless forloop.last check Add {% unless forloop.last %},{% endunless %} after each item
Price as integer (not decimal string) price_min in Shopify Liquid is in cents as an integer Use | divided_by: 100.0 to convert to decimal — outputs "139.99" not 13999
Image URL missing protocol Shopify img_url returns protocol-relative URL (//cdn.shopify.com/…) Prepend https: to the img_url output — schema.org URLs must be absolute

Frequently asked questions

Do Shopify collection pages have structured data by default?

Shopify collection pages output a BreadcrumbList JSON-LD block in most themes — and nothing else. There is no ItemList schema for products, no CollectionPage type signal, and no price range data available to AI agents. This makes collection pages effectively invisible for AI agent category queries.

What is ItemList schema and why does it matter for collections?

ItemList marks up an ordered list of items (products in a collection). Each ListItem has a position number, name, and URL. Adding ItemList to a collection page tells AI agents this page is a curated product list in a specific category with a specific ordering. Google AI Mode uses this data to surface collection pages in "best X" and category-level queries.

Should I use CollectionPage or ItemList schema for Shopify collections?

Use both, nested together. The outer type is CollectionPage (signals page purpose), with mainEntity pointing to an ItemList (signals product enumeration). This combination gives AI agents the page-type signal and the product listing structure they need for category query eligibility.

How many products should I include in ItemList for a collection?

Include all products visible on the first page — typically 24–48 products. Do not include products from subsequent paginated pages in the first page's ItemList. For large collections, prioritize your top-ranked products. Including more than 100 items in a single ItemList block may cause performance issues.

Check your collection page structured data

CatalogScan detects missing ItemList schema across all your Shopify collections and shows which category queries you're invisible for — with the exact Liquid code to fix it.

Scan your store free Read the blog