Start a project

Article · Technical SEO · AI search · llms.txt · 13 min read

How to write llms.txt that AI tools can use

llms.txt is a short markdown file at the root of your website that tells AI tools what the site is, who is behind it, and which pages are worth reading first. It is a convention, not a formal standard, and it does not replace robots.txt, a sitemap, or the meta tags on each page. Written accurately, it gives an assistant a clean map of the site instead of a guess built from a homepage and a few search snippets.

On this page 11 sections
  1. What llms.txt is, and what it is not
  2. What to put in the short index file
  3. When you also need llms-full.txt
  4. Where the files should live, and how they are served
  5. Allowing the crawlers that should read them
  6. Telling HTML pages that the file exists
  7. A worked example for a small UK site
  8. Common mistakes
  9. How to check the files
  10. Key takeaways
  11. Frequently asked questions

I keep both /llms.txt and a longer /llms-full.txt on leej.uk, and I built free tools for checking and writing them because I needed them on my own projects. What follows is that method.

What llms.txt is, and what it is not

The llms.txt proposal describes a markdown file at /llms.txt that starts with the project’s name, a short summary, and then sections of links, so a tool can fetch one predictable URL and get a trustworthy map of the site.

That is all it claims to be. It is not:

It should be a truthful description of what is actually there, the same habit I describe in the privacy manifests guide, aimed at assistants rather than App Review.

What to put in the short index file

The short file is an index, not a book. Its job is to be easy to fetch, easy to parse, and easy to trust. A useful structure looks like this:

  1. A heading with the site or project name. One h1. This is the name an assistant should use when it talks about you.
  2. A short summary, often as a blockquote. Two or three sentences: who it is for, what you do, where you are based if that matters. No slogans.
  3. A handful of official links. The website, a contact email, maybe a company number or a social profile you actually use. If an address or phone number is on the site, you can repeat it here; if it is not, do not invent one.
  4. Sections of links, each with a one-line description. Group pages the way a helpful person would: products, documentation, policies, writing, tools. Every link should work. Every description should match the page.

Here is a complete, imaginary file for a small UK bookshop. Nothing in it is taken from a live site; it is here so you can see the shape:

# North Harbour Books

> An independent bookshop in Whitby, selling new and used books in the shop and by post across the UK. We do not sell e-books or subscriptions.

- Website: https://example.com/
- Email: desk@example.com
- Phone: +44 1947 000000

## Visit and order

- [Opening hours and finding us](https://example.com/visit): hours, parking and the street entrance.
- [Order a book](https://example.com/order): pay online and collect in the shop, or have it posted.
- [Book clubs](https://example.com/clubs): current lists and how to join.

## Policies

- [Privacy](https://example.com/privacy): what we keep when you order, and for how long.
- [Returns](https://example.com/returns): how to send a book back.
- [Accessibility](https://example.com/accessibility): step-free access and large-print stock.

A few choices in that file are deliberate, and they apply to a developer site as much as to a shop:

On a site like this one, the same idea means listing the live projects, the developer tools, the articles and the legal pages, each with a sentence that matches the page, plus the contact details that already appear, including hello@leej.uk. If a section needs a paragraph of explanation, that paragraph belongs on the web page or in the fuller file described next. The index should stay a map.

When you also need llms-full.txt

The original proposal is one file. A second, longer file at /llms-full.txt is a pattern some sites, including this one, use when the short index is not enough for an assistant that wants the actual words on the pages.

The useful split is:

I generate the full file from the public HTML, not by pasting a second set of marketing lines. The moment the long file says something the live page does not, you have created a new source of truth, and it will drift. Rebuild it from the live pages, the same way I treat a release when I maintain an iOS app after launch.

A few practical limits help:

A ten-page brochure site with clear headings is often well served by the short index plus the pages themselves. Add the long file when you have many similar pages and you want an assistant to see the wording without crawling every URL. The llms-full.txt Builder turns clean page text into that file; the Markdown Mirror Generator is a useful way to see what a single page looks like once the markup is stripped.

Where the files should live, and how they are served

Put the short file at https://your-domain/llms.txt. That exact path is the one the proposal names, and it is the one tools will try first. If you also have a full file, put it at https://your-domain/llms-full.txt and mention it from the short file, so a client that only fetches the index still learns that the longer document exists.

A few serving details are easy to get wrong:

On a site served from a Cloudflare Worker, I treat these files as static assets in the same release as the HTML, so a deploy cannot ship a new article and an old index.

Allowing the crawlers that should read them

A file that is disallowed in robots.txt will not be fetched by a crawler that honours the file. That sounds obvious, and it is still the usual mistake. Decide who should be able to read the index — for many small UK sites, the search engines you already allow, plus the AI crawlers or fetchers you are comfortable with — then check the rules you already have.

A minimal, explicit approach is to allow the path for everyone you have not already blocked:

User-agent: *
Allow: /llms.txt
Allow: /llms-full.txt

Allow is only needed if a broader Disallow would otherwise hide those paths. If your robots.txt already allows the whole site, you do not have to list the files. If you have a rule such as Disallow: /, or you block unknown user agents, you do need the exception.

Two cautions:

User-agent tokens change, so I will not pretend a list here will stay complete. Use a current directory of crawler names, and review the rules when you change policy.

Telling HTML pages that the file exists

The proposal does not require a special HTML tag, but a link in the document head is useful for humans, for your own tools, and for any client that looks for it. On leej.uk each page includes links of this shape:

<link rel="describedby" href="https://leej.uk/llms.txt" title="llms.txt">
<link rel="llms-txt" type="text/plain" href="https://leej.uk/llms.txt" title="LLM summary for AI bots">
<link rel="llms-full-txt" type="text/plain" href="https://leej.uk/llms-full.txt" title="Full site text for AI bots">

rel="describedby" is a long-standing way to point at a description of the site. The llms-txt and llms-full-txt relations are more specific and less widely standardised, so treat them as a hint, not a contract. They are still worth adding, because they are cheap and unambiguous.

Your robots.txt can include a comment, but comments are for humans. The short llms.txt should link to /llms-full.txt if you have one, and can also point at /robots.txt or /sitemap.xml. This site lists those under a “Site files” section. Including /llms.txt in the sitemap is optional and harmless if the file is public.

A worked example for a small UK site

Imagine a three-person studio in Manchester that builds and maintains a few client sites, and also publishes a small set of free tools and notes. The homepage explains the work. There is a projects list, a contact page, a privacy policy, and eight short articles. That is already enough for a useful llms.txt, and not so much that you need a database to maintain it.

A first version can be written by hand in an hour: list every indexable URL from the sitemap or the main navigation; drop anything thin, duplicated, or only meant for you; write one sentence per remaining URL that a stranger could use to decide whether to open it; and write the two-sentence summary last. If the summary needs a claim that is not on any page, either add it to a page or drop it from the file.

When the list grows past a handful, generate the full file from the HTML and keep the short file curated. That is the pattern I use here. The articles index at /articles is the human map; /llms.txt points at it and at the individual guides; /llms-full.txt carries the readable text so an assistant does not have to guess from titles alone. The same discipline I use when I write about small, focused Apple apps applies: do not list work that is not actually available, and say so when something is still in production.

Common mistakes

The usual problems:

How to check the files

Before you announce anything, fetch the files the way a crawler would, not the way your browser shows a logged-in preview.

  1. Request the exact URLs. curl -sSI https://your-domain/llms.txt should show 200, HTTPS, and a text content type. Follow redirects and confirm that both www and the bare host end on the same document.
  2. Read the body. Is the markdown well formed? Do the links resolve? Do the descriptions still match the pages?
  3. Check robots.txt for the user agents you care about, including a sample of AI crawlers, and confirm that /llms.txt is allowed for the ones you intend to allow.
  4. Validate the file. The llms.txt Validator on this site checks the shape of the document and the obvious broken parts. It will not tell you whether a sentence is true; that is still your job.
  5. Compare the full file to the live pages if you have one. A section that has no counterpart on the site is a bug.

Re-run the checks when you add a section of the site, in the same release as the thing it describes.

Key takeaways

If you want a second pair of eyes on a file like this, tell me about it.

Frequently asked questions

What is an llms.txt file?

A markdown file served at /llms.txt that introduces the site in a few sentences and lists the important pages, each with a short description. It is a convention described at llmstxt.org, not a formal web standard.

Where should I put llms.txt on my website?

At the site root on your canonical host: https://example.com/llms.txt. If you use www or a trailing-slash policy, the file should follow the same redirects as the rest of the site. Do not bury it under /docs or /blog and expect tools to look there first.

What is the difference between llms.txt and llms-full.txt?

llms.txt is the short index. llms-full.txt is an optional, longer document some sites publish with the readable text of public pages. The short file should link to the long one when it exists. You do not need the long file if the site is small and the pages are already clear.

Do Google and ChatGPT both read llms.txt?

Not as a guarantee. Some AI tools fetch /llms.txt when they can find it; behaviour varies and it changes. I do not treat the file as something Google Search needs, and I do not treat it as a replacement for a sitemap or for ordinary HTML that already answers the question. Write it so it is accurate if a tool reads it, and keep the rest of your indexing in good order anyway.

Should llms.txt be listed in robots.txt or a sitemap?

It should be allowed in robots.txt for the crawlers you want to read it, which is often already true if you allow the whole site. Listing /llms.txt in a sitemap is optional. Mentioning /llms-full.txt from the short file is more important than listing it in robots.txt comments, which crawlers do not have to honour.

Written by Lee Johnson. Published 10 November 2026.

All articles · Swift A–Z · Apps

Questions, or an app in mind?

Let's bring your ideas to life. Whether you're envisioning a game-changing Apple Watch app or a transformative iOS experience, I'm here to make it happen.

Start a project