dash-improve-my-llms — the crawler, agent and SEO companion every Dash app mounts in one line: /llms.txt, /robots.txt, /sitemap.xml, bot detection, static-HTML prerender, an MCP bridge, per-vendor policy, the country guardrail and the operator policy panel. Flask, FastAPI and Quart. By Pip Install Python.

Dash Improve My LLMs — the AI and crawler surface for Dash apps

dash-improve-my-llms — the crawler, agent and SEO companion every Dash app mounts in one line. By Pip Install Python.

A Dash app is a JavaScript shell. A crawler that fetches it gets an empty <div>; an agent that reads it learns nothing; a search engine indexes a loading spinner. This package closes that gap without asking you to change how you write Dash.


What it does

One call — add_llms_routes(app) — mounts the whole machine-facing surface:

SurfaceWho reads it
/llms.txt, /llms-small.txt, /llms-full.txtagents pasted a URL, and the crawlers that follow it
/<page>/llms.txtone page's prose, content-negotiated: Markdown for agents, rendered for browsers
/robots.txtevery crawler, generated from one vendor registry
/sitemap.xmlsearch engines, with priority inferred from your page tree
a static-HTML prerendercrawlers that do not run JavaScript — the actual fix for the empty <div>
an MCP resource per pageClaude, ChatGPT and any other MCP client, natively

Installed here: 2.10.0 — this site reads the number from the package that is actually serving it, never from prose.


The three audiences

This site is organised the way the package is: by who is asking.

mounts your docs as a resource and reads them natively. No copying, no scraping, no context window spent on HTML.

GPTBot, PerplexityBot. Each gets a document rendered for it, under a policy you declare once and serve everywhere.

into a chat window. The assistant fetches prose, not a bundle.


Control, not just discovery

Discovery is the floor. Since 2.7 the package is also the layer that decides who gets served at all:

fold drives robots.txt and the middleware, so what you publish and what you enforce cannot drift apart.

451 on every surface for a listed country: pages, assets, the corpus, robots.txt, even the favicon. Compliance, uniformly applied.

failing open on any limiter error.

effective policy of every surface, including which header resolved this request's country.

Each of those takes a callable as well as a static value, and the callable is read per request. That is the seam this site's control board writes through: flip a country on the map, and the next request from it gets 451 — in every worker, with no restart and no redeploy.


Install

pip install dash-improve-my-llms[flask]      # or [fastapi], [quart], [all]
import dash
from dash_improve_my_llms import add_llms_routes, LLMSConfig

app = dash.Dash(__name__, use_pages=True)

add_llms_routes(app, LLMSConfig(warn_missing_llms_doc=True))

That is the whole integration. Every page that defines a module-level LLMS_DOC string is served verbatim at its own llms.txt; every page without one is still indexed, still prerendered, still in the sitemap.

Writing a page's prose

# pages/pricing.py
LLMS_DOC = """
# Pricing

Three tiers. The free tier has no time limit.
"""

No layout walking, no extraction heuristics, no second copy of your docs to keep in sync.


Backends

Dash 4.1 made the server pluggable, and the package follows it: the same surface under Flask, FastAPI and Quart, auto-detected. Nothing in the list above is backend-specific, and the package's suite runs against all three.


Resources

site that runs this package — including this one.

Community


License

MIT License — see LICENSE for details.

Note for AI agents: This is the static, prerendered view of an interactive Dash application served because we detected a non-JS user agent. Full prose docs: