What Broke When I Added Shopify Horizon Breadcrumbs
A merchant asked me to add Shopify Horizon breadcrumbs. The snippet worked for a day, then quietly broke on every multi-collection product.

Open your Horizon theme in the editor, add a product page block, and look at the block list. There is no breadcrumbs block. There is no breadcrumbs section either. If you go to Online Store > Themes > Edit code and grep the Horizon codebase for breadcrumb, you will find nothing that renders on a product page. That is not a settings issue: Shopify Horizon breadcrumbs are not shipped, and Shopify staff confirmed in August 2025 that they had no timeline for adding them.
What I checked first
I got a message from a home lighting merchant in September asking why the AI-generated breadcrumb snippet they had pasted into their Horizon theme was showing the wrong trail. Their product was a wall light, and the breadcrumb read "Home > Bedroom Lighting > Wall Light X" for every customer, even the ones who arrived from the Living Room collection or the Sale collection. They wanted the trail to reflect where the customer had actually clicked.
My first hypothesis was theme editor caching. Horizon caches section rendering, and I have seen it show stale output for two or three minutes after a change. I bumped a comment in the snippet, saved, hard-refreshed with the network tab open. The trail still read "Bedroom Lighting" for a customer who had arrived on the product from the Sale collection URL. Not a cache.
Second hypothesis: the AI-generated snippet was buggy. Solo merchants who paste Liquid code from ChatGPT sometimes get subtly wrong output, especially around array indexing. I opened the snippet. It was actually clean: 40 lines, collection.title and product.title referenced directly, no URL parsing (the "Home > Collections > Products > product-name" bug that shows up when someone reads request.path and prints the raw path segments). This was not a code quality issue.
Third hypothesis: the customer was arriving via search, and the snippet was falling back to some default collection. This turned out to be closer to the truth, but I had the mechanism wrong.
Where the snippet worked, then quietly stopped
I tested from the storefront. From the homepage, click Sale, click the wall light. Breadcrumb: "Home > Bedroom Lighting > Wall Light X."
The customer had been in Sale. Why did the breadcrumb say Bedroom Lighting?
I checked the URL. It was /products/wall-light-x, not /collections/sale/products/wall-light-x. Horizon was routing product clicks from collection pages to the canonical product URL and dropping the collection segment. By the time Liquid rendered the breadcrumb, there was no collection in the template scope. The snippet was correctly falling back to product.collections.first, and that first collection - based on the order the merchant had assigned them - was Bedroom Lighting.
The snippet was doing exactly what Liquid can do. Liquid renders server-side at page load from the product's assigned collections, not from the customer's session history or referrer. If Horizon strips the collection segment from the URL, there is no signal left for a Liquid-only breadcrumb to work with.
That was the moment I realized the Shopify Horizon breadcrumbs problem is not one problem. It is a stack of at least three, and every fix guide I could find addressed only one of them.
The clue I almost missed in the URL
I went back and checked what request.path contained on that page. It was /products/wall-light-x. No collection handle. The request.path contains col.handle heuristic from Pilotwolf's block-based breadcrumb (thread 568649 in the Shopify Community, May 2026) is the best Liquid-only workaround, and it works cleanly when the URL preserves the collection. Older Dawn behavior did preserve it. Horizon, at least on the version I was on, did not for this store.
I checked another product on the same store. Same behavior. I checked a demo Horizon store I keep for testing. Same behavior. The collection-in-URL preservation is theme-dependent and, in Horizon, depends on which storefront link component the theme uses to render the collection product grid. Some grids link to /products/x directly; the ones that link to /collections/y/products/x are the ones that keep the breadcrumb signal intact.
This is the kind of thing I only find because a merchant sits me down with a specific complaint. Nothing in Shopify's docs, and nothing in the community threads I read for this article, says out loud "your Horizon collection grid may or may not preserve the collection segment, and that decides whether any Liquid breadcrumb approach can reflect the customer's actual navigation." Developer tim_tairli, in the January 2026 breadcrumb-structure thread, gets closest by pointing out that collection-aware product URLs create duplicate indexable paths and eat crawl budget, which is exactly why some themes strip them. The SEO tradeoff and the breadcrumb tradeoff are two sides of the same design decision.
What Liquid can and cannot know
I ended up sketching this out on paper for the merchant.
If the URL is /collections/sale/products/wall-light-x, Liquid knows the collection is Sale, and any snippet that references the collection object or checks request.path against product.collections will produce the correct breadcrumb.
If the URL is /products/wall-light-x, Liquid does not know how the customer got there. It can look at product.collections.first, which is arbitrary. It can look at the Referer header, but that header is not exposed to Liquid, and Shopify does not offer a way to read it. It can look at a ?from=sale query parameter if you add one, but nothing in Horizon adds one automatically.
That leaves three options for the merchant who wants correct multi-collection Shopify Horizon breadcrumbs:
- Force the collection segment to stay in the URL by editing every product link in every collection template to output
/collections/{{ collection.handle }}/products/{{ product.handle }}. This gives you the right breadcrumb and doubles or triples your indexable URL space, which is the crawl budget problem tim_tairli named. - Use a product metafield to designate one "canonical" collection per product, and always render that in the breadcrumb regardless of where the customer came from. This is deterministic and consistent for SEO. It is also work: you have to define the metafield, populate it for every product, and keep it current as new products get added.
- Render breadcrumbs client-side in JavaScript using session history or a first-party cookie set on collection page views. This is how most non-Shopify e-commerce platforms handle it. It also breaks for customers with JavaScript disabled, which developer pierrewebdev flagged in December 2022 without anyone resolving. I have not seen a working, accessible community implementation for Shopify in the years since.
Every one of these has a real cost. There is no free fix for Shopify Horizon breadcrumbs on a multi-collection catalog. The right answer depends on whether you care more about SEO consistency, navigation accuracy, or maintenance overhead, and different merchants land in different places.
What I almost shipped that would have made things worse
The AI-generated snippet the merchant had pasted included a <script type="application/ld+json"> BreadcrumbList block at the bottom. I was about to keep it. Then I opened the theme's original theme.liquid and found that the ancestor code in this Horizon fork already emitted a BreadcrumbList as microdata inline on the built-in breadcrumb (which Horizon had removed the visual for but not the schema fragment for). The AI snippet's JSON-LD block would have coexisted with a partial microdata leftover, which is the sort of setup that makes Google Search Console show partial validation and gives you an hour of debugging you did not need.
I removed the leftover microdata fragment, kept the JSON-LD, and validated the product page in Google's Rich Results Test before pushing. This is the specific mistake documented in Shopify Community thread 290950 (January 2024): a merchant added visual breadcrumbs, their GSC breadcrumb count declined, and the cause was accidentally deleted schema markup. My variant was the opposite direction (two schema blocks fighting), and the diagnostic is the same: use the Rich Results Test on one product page, not GSC's aggregate count, because the aggregate count reflects crawl coverage rather than markup accuracy.
If you are staring at your own snippet and unsure whether the schema is intact, that is a specific thing a help1 expert can check with you in the first 15 free minutes, because it takes about three minutes to read and about an hour to guess at.
What I actually shipped
For this merchant, we picked option 2: a product metafield for canonical collection. The store had roughly 400 SKUs, most in three or four collections apiece. We defined a custom.primary_collection metafield of type "collection reference," populated it via a bulk CSV upload from a spreadsheet the merchant already used for merchandising, and updated the snippet to prefer the metafield value over product.collections.first. The Liquid change was six lines.
I would not pick this for every store. If you have 5,000 products and no existing spreadsheet, populating the metafield is a real project. For a merchant with a small catalog who cares about SEO more than exact navigation reflection, the metafield route is calm and consistent. For a merchant with a large catalog and a clear taxonomy, option 1 (keep the collection segment in URLs) is worth the crawl budget cost as long as you also add canonical link tags. For a merchant whose visitors mostly land from search on the canonical product URL anyway, none of this matters much, because product.collections.first is what most people see regardless.
If your store is running Horizon and you are about to add Shopify Horizon breadcrumbs from a paste-in snippet, run a quick test before you commit. Visit a multi-collection product from three different collection pages. Read the breadcrumb each time. If it is the same trail three times, your URL strategy has already decided the answer for you, and no snippet upgrade is going to change it. Fix the URL strategy first, or accept the metafield route, and stop trying to squeeze accurate history-based breadcrumbs out of Liquid alone. Also worth a look while you are in the theme code: the common Horizon audit findings I keep running into tend to cluster in the same three files, and breadcrumbs are one of them.
What I stopped saying
I used to recommend "just paste this Liquid snippet" as the standard breadcrumb fix, and I was wrong about that for two years, because the snippet only works in the two-collection case and fails silently everywhere else. The honest answer for Shopify Horizon breadcrumbs is that Shopify has a data-model gap and a URL-strategy gap, Liquid cannot bridge both, and pasting a snippet does not decide which tradeoff you want.
Still stuck? Talk to an expert.
Our vetted Shopify experts can fix this issue for you in a live session. $39 per session. Your first 15 minutes are free.