← Blog

So baust du eine shadcn/ui-Registry, die Claude Code und Cursor wirklich nutzen können

Eine shadcn-Registry ist 2026 nur die halbe Arbeit. Namespaces, Markdown-Docs unter .md-URLs, llms.txt, ein MCP-Server und private Registries, damit KI-Agenten sie richtig installieren.

Preet Suthar · · 5 Min. Lesezeit

  • shadcn/ui
  • AI
  • React
  • Developer tools

Die meisten shadcn/ui-Komponenten werden inzwischen von einem KI-Coding-Agenten installiert, nicht von einer Person, die den Befehl eintippt. Wenn du eine Registry veröffentlichst, ist der Agent dein Nutzer. Er muss deine Komponenten finden, ihre Props lesen, ohne zu raten, und den richtigen Installationsbefehl ausführen. Eine Registry, die nur für Menschen funktioniert, die sich durch eine Docs-Site klicken, ist eine Registry, die falsch benutzt wird.

Ich betreibe HextaUI, eine shadcn/ui-Registry, und habe einen guten Teil dieses Jahres damit verbracht, sie für Claude Code, Cursor und den shadcn MCP-Server tauglich zu machen. Das hier ist alles, was sich als wichtig herausgestellt hat, in der Reihenfolge, in der ich es wieder machen würde.

1. Liefere eine Registry, die die Validierung besteht

Fang mit den Grundlagen an. Jedes Item ist eine JSON-Datei nach dem Registry-Schema, mit name, type, files, dependencies und registryDependencies. Lege den Index unter eine stabile URL und jedes Item unter eine vorhersehbare:

https://your-site.com/r/registry.json
https://your-site.com/r/button.json
https://your-site.com/r/all.json

Führe shadcn build aus, um sie aus einer registry.json-Quelle zu erzeugen, und validiere vor dem Deploy. Die CLI hat im Mai 2026 einen Validierungsschritt für Registries bekommen. Eine Registry, die die Validierung nicht besteht, scheitert für Agenten lautlos, und die schreiben die Komponente dann von Hand und machen es falsch.

Zwei Details, die einen echten Unterschied machen:

  • registryDependencies mit vollständigen URLs. Wenn dein Dialog von deinem Button abhängt, verweise auf https://your-site.com/r/button.json, nicht auf button, sonst zieht die CLI stattdessen den shadcn/ui Button.
  • Ein all.json-Item, das von allem abhängt. Agenten, die „das Designsystem einrichten“ sollen, greifen danach.

2. Registriere einen Namespace

Seit es Registry-Namespaces gibt, trägt ein Nutzer das hier in components.json ein:

{
  "registries": {
    "@hextaui": "https://hextaui.com/r/{name}.json"
  }
}

Und installiert dann mit einem kurzen Namen:

npx shadcn@latest add @hextaui/dialog

Dokumentiere dieses Snippet auf deiner Installationsseite und in deiner llms.txt. Die Kurzform ist das, was der shadcn MCP-Server durchsucht; eine Registry ohne Namespace ist also für das eine Tool unsichtbar, mit dem die meisten Agenten Registries durchstöbern.

Ist die Registry privat, nimmt die Objektform Header mit Umgebungsvariablen entgegen, die die CLI auflöst und nie loggt:

{
  "registries": {
    "@acme-pro": {
      "url": "https://acme.com/r/pro/{name}.json",
      "headers": {
        "Authorization": "Bearer ${ACME_TOKEN}"
      }
    }
  }
}

3. Gib jeder Docs-Seite einen Markdown-Zwilling

Agenten lesen HTML schlecht. Markdown lesen sie gut. Lass jede Docs-URL unter .md mit demselben Inhalt antworten: Beschreibung, Installationsbefehl, vollständiger Quellcode, Verwendung, Beispiele, Tastaturunterstützung und die API-Tabelle.

https://hextaui.com/docs/button      -> HTML for people
https://hextaui.com/docs/button.md   -> Markdown for agents

Schreib das Markdown nicht von Hand. Erzeuge es aus derselben Quelle wie die Seite, damit die beiden nie auseinanderlaufen. Bei HextaUI läuft die .md-Route durch den React-Baum der Seite und serialisiert ihn; ein neues Beispiel auf der Seite landet also automatisch im Markdown.

Die API-Referenz zählt hier am meisten. Ein Agent, der eine Props-Tabelle lesen kann, halluziniert kein size="xl", das es nicht gibt.

4. Veröffentliche llms.txt und llms-full.txt

llms.txt ist ein Markdown-Index im Root deiner Site: was das Projekt ist, wann man es nutzt, wann nicht, wie man es installiert, und eine Zeile pro Docs-Seite mit ihrem .md-Link. llms-full.txt ist jede Docs-Seite aneinandergehängt, für Agenten, die alles auf einmal laden wollen.

Der Abschnitt „wann du es nicht nutzen solltest“ ist der Teil, den alle überspringen, und der Teil, der dir Support-Tickets erspart. Wenn deine Registry nur React und Tailwind unterstützt, sag es, sonst versucht ein Agent, sie in ein Vue-Projekt zu installieren.

Halte den Installationsbefehl in den ersten zehn Zeilen. Agenten lesen den Anfang.

5. Betreibe einen MCP-Server, nur lesend, ohne Key

Die shadcn CLI hat einen eigenen MCP-Server (npx shadcn@latest mcp), der jede Registry in components.json durchsucht. Das deckt Installationen ab. Docs, Tastaturbelegungen oder Beispiele deckt es nicht ab.

Deshalb betreibe ich einen zweiten unter https://hextaui.com/mcp, Streamable HTTP, nur lesend, ohne API-Key, mit fünf Tools: search_docs, get_component, get_component_api, get_examples und get_install_command. Claude Code verbindet sich mit einer Zeile:

claude mcp add --transport http hextaui https://hextaui.com/mcp

Cursor und VS Code nehmen dieselbe URL in ihrer MCP-Konfiguration. Einmal verbunden, wird aus „add a HextaUI combobox with async results“ eine Docs-Suche, ein API-Lesen und der richtige Installationsbefehl, ohne Raten dazwischen.

Mach ihn auch auffindbar. Veröffentliche eine Server Card unter /.well-known/mcp/server-card.json und eine server.json im Format der MCP-Registry. Agenten und die Tools um sie herum schauen zunehmend zuerst dort nach.

6. Beschreibe die HTTP-Schnittstelle mit OpenAPI und echten Fehlern

Alles oben ist auch einfaches HTTP, und Agenten rufen HTTP zunehmend direkt auf. Veröffentliche eine openapi.json mit Operation-IDs und typisierten Antworten. Gib Fehler als RFC 9457 application/problem+json zurück, mit einem resolution-Feld, das sagt, was als Nächstes zu tun ist:

{
  "type": "https://hextaui.com/docs/api#not-found",
  "title": "Component not found",
  "status": 404,
  "detail": "No component named 'modal'.",
  "resolution": "Try 'dialog' or 'alert-dialog'. The catalog is at /mcp/index.json."
}

Ein Agent, der eine 404 mit Hinweis bekommt, fängt sich wieder. Ein Agent, der eine HTML-Fehlerseite bekommt, schreibt die Komponente aus dem Gedächtnis.

7. Liefere eine Skill-Datei

Claude Code und eine wachsende Zahl von Agenten lesen SKILL.md-Dateien, die erklären, wie man ein Tool benutzt. Lege eine unter /.well-known/agent-skills/<name>/SKILL.md ab: wie man eine Komponente findet, ihre Docs liest und sie installiert, mit den exakten Befehlen. Es ist eine Seite Markdown und die Seite mit der größten Hebelwirkung auf der ganzen Site.

8. Teste mit den Agenten, nicht mit dir selbst

Öffne ein frisches Next.js-Projekt in Claude Code, mit angebundenem MCP-Server und ohne weiteren Kontext. Bitte es: „add a date picker from <your registry> with a range and a disabled weekend rule“. Schau zu, was es tut. Jede falsche Vermutung ist eine Lücke in deinen .md-Docs oder deiner llms.txt.

Dann dasselbe in Cursor, nur mit llms.txt und ohne MCP. Dann mit nichts als der URL. Die Registry sollte über alle drei Stufen sauber abfallen.

Was du davon hast

Ein Agent mit angebundenem MCP-Server oder den .md-Docs liest die Props-Tabelle, statt sie zu raten, führt den Installationsbefehl aus, statt die Komponente neu zu schreiben, und installiert die Abhängigkeiten in der richtigen Reihenfolge. Die Registry-Seite von HextaUI war etwa eine Woche Arbeit. Die Agenten-Seite hat länger gedauert, und sie ist der Teil, der die Registry für die nutzbar gemacht hat, die heute den Großteil der Installationen erledigen.

Wenn du dir alles live ansehen willst: hextaui.com/llms.txt, jede Docs-Seite mit angehängtem .md, die MCP-Docs und die API-Docs mit der OpenAPI-Spezifikation.

Häufige Fragen

Brauche ich einen eigenen MCP-Server, wenn die shadcn CLI schon einen hat? Der shadcn MCP deckt Suche und Installation über alle Registries in components.json ab. Dein eigener Server deckt Docs, APIs und Beispiele ab. Die meisten Registries profitieren von beiden.

Sollte der MCP-Server einen API-Key verlangen? Nicht für öffentliche Docs. Jeder Key, den du verlangst, ist ein Agent, der aufgibt. Hebe Auth für private Items auf und nutze Bearer-Tokens über Header in components.json.

Wie erzeuge ich die Markdown-Docs, ohne Inhalte zu duplizieren? Rendere denselben Komponentenbaum, den die Seite nutzt, und serialisiere ihn zu Markdown. Eine Quelle, zwei Formate.

Was gehört in llms.txt? Eine Beschreibung, wann man es nutzt und wann nicht, der Installationsbefehl, das Namespace-Snippet und eine Zeile pro Docs-Seite mit Link auf ihre .md.