← Back to Daeri

Tutorial

Implementing llms.txt on Shopify: A Step-by-Step Technical Tutorial

Step-by-step tutorial to create, deploy, and verify llms.txt on Shopify so ChatGPT, Claude, and AI shopping agents can read your store.

AI shopping agents — ChatGPT, Claude, Perplexity, and the dozens of vertical tools built on them — are starting to browse the web on behalf of shoppers. Before they recommend your products, they need to understand what your store sells. The llms.txt convention gives them a curated, machine-readable map of your site in under a page.

This tutorial is for Shopify developers and technically-minded merchants. By the end, you will have a live /llms.txt endpoint, a working redirect, and a verification script you can run to confirm agents can read it.

Prerequisites

  • A Shopify store on any plan (Online Store channel must be active).
  • Admin access with permission to edit themes and create pages.
  • Optional but recommended: a reverse proxy layer (Cloudflare, Vercel, or your own CDN) if you want the cleanest setup.

Step 1: Write your llms.txt content

The file is plain Markdown. The spec (proposed by Jeremy Howard) expects an H1 store name, a one-line blockquote summary, then H2 sections with bullet links to the canonical URLs you want agents to index.

Here's a production-ready template for a Shopify store:

# Oak & Timber

> Oak & Timber hand-makes solid-wood furniture in Portland, Oregon. We ship across the US and Canada with white-glove delivery available in the Pacific Northwest.

## Collections
- [All furniture](https://oakandtimber.com/collections/all): Browse sofas, tables, beds, and storage.
- [Sofas & seating](https://oakandtimber.com/collections/sofas): Fabric and leather options in custom dimensions.
- [Dining tables](https://oakandtimber.com/collections/dining-tables): Extendable hardwood tables, seats 4–12.
- [Bedroom](https://oakandtimber.com/collections/bedroom): Beds, nightstands, and dressers.

## Policies
- [Shipping](https://oakandtimber.com/policies/shipping-policy): Free US shipping over $500; white-glove delivery in OR/WA/CA/ID.
- [Returns](https://oakandtimber.com/policies/refund-policy): 30-day returns on unused items; custom orders final sale.
- [Warranty](https://oakandtimber.com/policies/warranty): 10-year structural warranty on all frames.

## Sitemap
- [sitemap.xml](https://oakandtimber.com/sitemap.xml)

## Optional
- [About us](https://oakandtimber.com/pages/about-us): Our story, workshop tours, and sustainability practices.
- [Care guide](https://oakandtimber.com/pages/care): How to maintain solid wood furniture over decades.

Rules to follow:

  • Keep it under 60 lines. Agents have context windows; brevity wins.
  • Use absolute URLs with https://. Relative paths are not reliably resolved by all agents.
  • Include your sitemap link so the agent can discover every product, not just the ones you listed.
  • Put policies in plain text — agents read these to assess trust before recommending a purchase.
  • Be explicit about what you don't do (e.g., "custom orders final sale", "no international shipping") to prevent bad recommendations.

Step 2: Create the Shopify page template

Shopify does not serve raw Markdown at /llms.txt out of the box, so you need a custom page template that strips theme chrome and outputs plain text with a text/plain content type.

2A. Add the template file

  1. In your Shopify admin, go to Online Store → Themes.
  2. Click the menu on your active theme and choose Edit code.
  3. In the left sidebar, under Templates, click Add a new template.
  4. Select Page as the template type, name it llms, and choose liquid format.
  5. Replace the generated content with the following Liquid code:
{% layout none %}
{% comment %}
  llms.txt template for Shopify
  Outputs raw Markdown with a text/plain content-type header.
  Assign this template to a page with handle "llms-txt".
{% endcomment %}

{% capture output %}
# {{ shop.name }}

> {{ shop.description | default: shop.name | append: " — online store" }}

## Collections
{% for collection in collections limit: 5 %}
- [{{ collection.title }}]({{ shop.url }}{{ collection.url }}): {{ collection.description | strip_html | truncate: 120 }}
{% endfor %}

## Policies
- [Shipping]({{ shop.url }}/policies/shipping-policy)
- [Returns]({{ shop.url }}/policies/refund-policy)
- [Privacy]({{ shop.url }}/policies/privacy-policy)
- [Terms of Service]({{ shop.url }}/policies/terms-of-service)

## Sitemap
- [sitemap.xml]({{ shop.url }}/sitemap.xml)
{% endcapture %}

{{ output | strip_newlines | replace: '  ', '' }}

{% layout none %} removes the theme wrapper. The capture block builds the Markdown string, then we strip extra whitespace before output. Shopify will serve this as text/html by default, which is fine — agents read the raw text regardless — but for correctness you can also set the content type via a small app proxy if you have one.

2B. Create the page and assign the template

  1. Go to Online Store → Pages in your Shopify admin.
  2. Click Add page.
  3. Set the Title to "LLMs txt" (this is only for admin reference).
  4. Set the URL handle to llms-txt (this is critical — it must be llms-txt).
  5. In the right sidebar, under Theme template, select page.llms.
  6. Leave the body content empty — the template generates everything dynamically.
  7. Click Save.

Your page is now live at https://yourstore.com/pages/llms-txt. Test it in a browser: you should see raw Markdown with no theme header, navigation, or footer.

Step 3: Add the redirect from /llms.txt

The convention expects the file at /llms.txt, not /pages/llms-txt. Shopify's built-in URL redirects can handle this.

  1. Go to Online Store → Navigation.
  2. Click View URL redirects (top right).
  3. Click Create URL redirect.
  4. Set Redirect from to /llms.txt.
  5. Set Redirect to to /pages/llms-txt.
  6. Click Save redirect.

Wait 30 seconds for the redirect to propagate, then open https://yourstore.com/llms.txt. You should see your Markdown content.

Step 4: Hardcode a fully custom version (optional)

The dynamic template above pulls from your collections and shop metadata. If you want complete control over every line — for example, to write custom policy summaries or exclude specific collections — replace the dynamic Liquid with a static Markdown block:

{% layout none %}

# Your Store Name

> Your custom one-line summary goes here.

## Collections
- [All products](https://yourstore.com/collections/all): Full catalog.
- [Collection A](https://yourstore.com/collections/collection-a): Description.
- [Collection B](https://yourstore.com/collections/collection-b): Description.

## Policies
- [Shipping](https://yourstore.com/policies/shipping-policy): Free shipping over $50.
- [Returns](https://yourstore.com/policies/refund-policy): 30-day returns.

## Sitemap
- [sitemap.xml](https://yourstore.com/sitemap.xml)

Hardcoding is the approach we recommend for most merchants: it avoids surprises when you rename a collection, and it lets you craft descriptions specifically for an AI reader rather than reusing collection SEO copy.

Step 5: Verify it works

Run these three checks before calling the implementation done.

Check 1: Direct curl

curl -s https://yourstore.com/llms.txt | head -n 10

You should see your Markdown H1 and summary, not HTML tags.

Check 2: No theme wrapper

curl -s https://yourstore.com/llms.txt | grep -i "<html" | wc -l

Result should be 0. If you see <html> or <div>, the {% layout none %} tag is missing or your theme ignores it.

Check 3: Agent comprehension

Ask ChatGPT, Claude, or Perplexity: "What does yourstore.com sell?" or "Summarize the return policy for yourstore.com." If the answer matches what you wrote in llms.txt, the agent is reading it. If the answer is vague or wrong, the agent may be relying on old crawl data — wait 24–48 hours and retry.

Step 6: Advanced — serve via reverse proxy

If your store sits behind Cloudflare, Vercel, or a custom CDN, the cleanest approach is to serve /llms.txt as a static file directly from the edge and bypass Shopify entirely.

Cloudflare Workers example

export default {
  async fetch(request, env, ctx) {
    const url = new URL(request.url);
    if (url.pathname === '/llms.txt') {
      return new Response(await env.STORE_BUCKET.get('llms.txt'), {
        headers: { 'Content-Type': 'text/plain; charset=utf-8' },
      });
    }
    return fetch(request);
  },
};

Vercel example

Place a file named llms.txt in your project's public/ directory. Vercel serves/llms.txt automatically with the correct content type. This is the simplest setup if you already host a headless storefront on Vercel that proxies to Shopify.

Common mistakes

  • Using relative URLs. Agents resolving your store from different contexts may not resolve/collections/all correctly. Always use full https:// URLs.
  • Forgetting the redirect. If /llms.txt 404s, most agents will skip your store entirely. The redirect is not optional.
  • Wrapping in HTML. Some themes inject tracking scripts or cookie banners even with {% layout none %}. Verify with curl that the output is plain text.
  • Listing too much. A 200-line file defeats the purpose. Curate 3–5 collections, 3–5 policy links, and a sitemap. Let the sitemap handle comprehensiveness.

How this affects your Daeri score

In the Daeri Agent-Readiness Score, llms.txt lives under the Discoverability dimension — the measure of whether an AI agent can find and correctly understand your store on the first pass. Stores that add a clean llms.txt typically gain 10–15 points here, often the largest single improvement available.

Want to see your current score? Run a free Daeri audit and we'll tell you exactly what's missing — and whether your llms.txt is being picked up by real agents.