Blog

Wat een agent-ready website nodig heeft: notities bij het bouwen van dardo.studio

We maakten dardo.studio leesbaar en aanroepbaar voor AI-agents, laag voor laag. Dit doet elke laag, wie het lezen ervan vandaag documenteert en welke lagen we opnieuw zouden bouwen.

Door Nicolás Cerón ·

Een kleine robot op wielen volgt 's nachts in een museumzaal een karmozijnrode geleidelijn naar een verlicht beeld.

Het korte antwoord

Een agent-ready website doet drie dingen. AI-agents kunnen er komen. Ze kunnen de site lezen zonder zich door menu's, banners en scripts te worstelen. En waar dat zinvol is, kunnen ze een paar gedeclareerde tools aanroepen in plaats van te raden op welke knop ze moeten drukken.

We bouwden alle drie in dardo.studio in oktober 2026. Hier lees je wat we hebben opgeleverd en in hoeverre de grote AI-platforms documenteren dat ze het gebruiken, gecontroleerd op de live site op 8 oktober 2026.

De samenvatting is minder spannend dan de meeste "AI-ready"-checklists. De oudste lagen wegen het zwaarst: toegang voor crawlers en schone, semantische HTML. Markdown-kopieën en llms.txt zijn goedkope extra's. MCP, A2A en WebMCP zijn echte protocollen met werkende clients, maar in geen van de crawlerdocumentaties die we citeren van OpenAI, Anthropic, Perplexity of Google staat dat hun assistenten de tools van een site zelf vinden.

Begin met toegang: robots.txt en de edge

In onze robots.txt staat dezelfde groep regels voor de standaardagent (*) en voor elke AI-zoekcrawler en user fetcher die we noemen:

User-agent: OAI-SearchBot
Allow: /
Disallow: /api/
Content-Signal: search=yes, ai-input=yes

Dezelfde regels gelden voor ChatGPT-User, PerplexityBot, Perplexity-User, Claude-SearchBot, Claude-User en Bingbot. Alleen /api/ is afgesloten.

Zoekcrawlers en trainingscrawlers zijn aparte dingen

De grote bedrijven documenteren inmiddels aparte tokens voor zoeken en voor training:

  • OpenAI. OAI-SearchBot zorgt dat sites verschijnen in ChatGPT-zoekresultaten. Sites die de bot blokkeren, ontbreken in de antwoorden van ChatGPT-zoekopdrachten, al kunnen ze nog wel als gewone navigatielinks verschijnen. GPTBot verzamelt trainingsdata. (OpenAI-crawlers)
  • Anthropic. Claude-SearchBot indexeert voor zoeken, ClaudeBot verzamelt trainingsdata en Claude-User haalt pagina's op wanneer iemand Claude iets vraagt. (Anthropic-crawlers)
  • Perplexity. PerplexityBot toont sites en linkt ernaar in de resultaten van Perplexity en wordt niet gebruikt om foundation models te trainen. (Perplexity-crawlers)
  • Google. Google-Extended is een controletoken voor training van Gemini en grounding in andere Google-producten. Het heeft geen invloed op opname of ranking in Google Zoeken. (Google common crawlers)

Door gebruikers getriggerde fetchers zijn anders. OpenAI zegt dat robots.txt mogelijk niet geldt voor ChatGPT-User, omdat een persoon die verzoeken start. Perplexity-User en de door gebruikers getriggerde fetchers van Google negeren het over het algemeen. Deze fetchers handelen in realtime namens één persoon; waar een blokkade werkt, houdt die vooral de assistent van die persoon tegen om je pagina te lezen.

In ons bestand staan de trainingscrawlers niet vermeld, dus vallen ze onder * en zijn ze toegestaan. Dat is een zakelijke keuze, en de aanbieders documenteren het als een aparte instelling: GPTBot of ClaudeBot blokkeren is niet hetzelfde als hun zoekindex verlaten.

Content Signals: één regel, geen verplichtingen

De regel Content-Signal komt uit het Content Signals Policy van Cloudflare, dat drie vormen van gebruik noemt: search, ai-input (content aan een model voeden op het moment van antwoorden) en ai-train. Wij laten ai-train weg, wat volgens het beleid dat gebruik noch toestaat noch beperkt. Cloudflare zegt dat signalen voorkeuren uitdrukken, niets blokkeren en genegeerd mogen worden. Geen van de hier geciteerde crawlerpagina's noemt ze. Het kost één regel; verwacht er voorlopig niets van.

Controleer de edge, niet alleen het bestand

robots.txt beschrijft een beleid; je CDN bepaalt wat er gebeurt. Toen we op 2 oktober testten, beantwoordde Cloudflare's Browser Integrity Check de standaard HTTP-client van Python (Python-urllib) en libwww-perl met een 403, terwijl robots.txt alles toestond. Scripts van coding agents gebruiken vaak ongewijzigd de standaardbibliotheek van Python.

We voegden een configuratieregel in Cloudflare toe die GET- en HEAD-verzoeken voor publieke content vrijstelt; /api/ geeft nog steeds een 403. Dezelfde review ontdekte dat onze .txt-bestanden geen charset hadden, waardoor sommige clients "Bogotá" lazen als "Bogotá". De oplossing was één header: charset=utf-8.

Test met echte verzoeken onder elke user agent. Zo zie je dat niets de naam blokkeert; het bewijst niet dat de echte crawler langskwam.

Eenvoudige, semantische HTML: de laag waar elke agent op leunt

De AI-optimalisatiegids van Google beschrijft browseragents die screenshots analyseren, de DOM inspecteren en de toegankelijkheidsboom interpreteren. Die verwijst sitebeheerders naar de agent-vriendelijke richtlijnen van web.dev, die grotendeels neerkomen op toegankelijkheidswerk: gebruik <button> en <a> in plaats van opgemaakte <div>s, koppel elk label aan zijn invoerveld en voorkom dat de layout verspringt onder een screenshot.

Op dardo.studio heeft elke pagina één <main> en gelabelde <nav>-landmarks. Menu- en themaschakelaars zijn echte knoppen die hun status melden met aria-expanded en aria-pressed, en gesloten menu's zijn inert. Elk veld van het contactformulier staat binnen zijn <label>, wat het een toegankelijke naam geeft. web.dev stelt het attribuut for voor; het invoerveld omwikkelen doet hetzelfde.

Dit helpt nu al gebruikers van schermlezers, en dat is reden genoeg.

Een schone markdown-kopie van elke pagina

Agents betalen voor elk token dat ze lezen, en een gerenderde pagina bevat navigatie, een cookiebanner, scripts en decoratieve afbeeldingen. Vóór dit werk gaf een verzoek om onze pagina's met Accept: text/markdown dat allemaal terug als HTML.

Nu schrijft een buildstap naast elke indexeerbare pagina een index.md. Die begint met front matter (titel, beschrijving, canonieke URL, taal, de versie in de andere taal en de updatedatum), gevolgd door de <main>-inhoud van de pagina zonder scripts, knoppen, decoratieve afbeeldingen of de inhoudsopgave op de pagina. Antwoorden uit de FAQ blijven staan. Formulieren worden een lijst met hun velden en keuzes, zodat een agent iemand kan vertellen wat ons contactformulier vraagt zonder het te gebruiken.

Er zijn drie manieren om de kopie op te halen:

  • Stuur Accept: text/markdown mee naar de gewone URL. Die antwoorden bevatten Vary: Accept, zodat caches de versies gescheiden houden.
  • Vraag het bestand op: /en/services/seo/index.md.
  • Voeg .md toe aan het paginapad (/en/services/seo.md). Voor URL's die op een slash eindigen gebruikt het llms.txt-voorstel index.md, de vorm hierboven.

Elke HTML-pagina verwijst bovendien naar haar kopie met <link rel="alternate" type="text/markdown">.

Wijs zoekmachines terug naar de HTML

Volgens de richtlijnen van Google kan het naast HTML ook veel andere bestandstypen crawlen en indexeren, zonder ze speciaal te behandelen. Een markdownkopie zou kunnen concurreren met de eigen pagina, dus elk markdownantwoord noemt de HTML-pagina als canonieke versie:

$ curl -sI https://dardo.studio/en/services/seo/index.md
content-type: text/markdown; charset=utf-8
link: <https://dardo.studio/en/services/seo/>; rel="canonical", ...

Wie leest deze kopieën? Cloudflare bouwde Markdown for Agents om HTML aan de edge om te zetten voor verzoeken die de voorkeur geven aan markdown, wat erop wijst dat agents erom vragen. Er staat niet bij welke clients de header sturen, en wij hebben ook geen geverifieerde lijst. Gebruik je de functie van Cloudflare, dan voegt die Content-Signal: ai-train=yes, search=yes, ai-input=yes toe, tenzij je origin een eigen waarde instelt. Wij genereren onze kopieën tijdens de build, zodat ze exact overeenkomen met de pagina.

llms.txt: een nuttige index zonder effect op zoeken

llms.txt is een voorstel van Jeremy Howard, voor het eerst gepubliceerd in september 2024 en nog open voor input van de community: een markdownbestand op /llms.txt met de naam van de site, een korte samenvatting en lijsten met links die een agent nodig kan hebben.

Ons bestand, op /llms.txt en /es/llms.txt, wordt gegenereerd uit dezelfde data als de pagina's, dus het kan niet afwijken. Het vermeldt de feiten over de studio (Bogotá, opgericht in 2026, een team van drie, hoe projecten geprijsd worden, contactmogelijkheden), somt diensten en werk op en legt uit hoe je markdownkopieën ophaalt. llms-full.txt bevat de volledige tekst van de studio-, dienst-, werk- en contactpagina's.

Eén regel noemt bedrijven met een vergelijkbare naam die niet wij zijn. Toen we op 2 oktober keken, stonden zij bovenaan de zoekresultaten voor "dardo studio". Die regel is misschien wel de nuttigste van het bestand.

De stand van zaken, kort en duidelijk:

  • Google zegt dat je llms.txt niet nodig hebt om in Search of de AI-functies te verschijnen, dat Search het negeert en dat het hebben van een bestand niet helpt en ook niet schaadt.
  • OpenAI, Anthropic en Perplexity zeggen in hun crawlerdocumentatie niet dat hun bots de llms.txt van andere sites lezen. De eigen documentatiesites van OpenAI, Anthropic en Perplexity publiceren er wel een, voor agents die hun docs lezen.

Houd er een aan als hij gegenereerd en juist is. Het helpt coding agents en tools die ernaar zoeken. Het is geen hefboom voor zichtbaarheid.

Tools die agents kunnen aanroepen: MCP, A2A en de API-catalogus

We hebben twee alleen-lezen tools gepubliceerd:

  • list_services geeft onze gepubliceerde diensten, scope, opleveringen en bron-URL's terug in het Engels of Spaans, gefilterd op een optioneel trefwoord.
  • get_project_brief geeft de vragen terug die je beantwoordt voordat je contact met ons opneemt, plus de gelokaliseerde contactlink voor die dienst.

Eén implementatie zit achter meerdere toegangspunten:

ToegangspuntAdres op dardo.studioStandaard en status
MCP-server/mcp, kaart op /.well-known/mcp/server-card.jsonMCP Streamable HTTP; de servercard is een conceptvoorstel
A2A-agent/a2a, kaart op /.well-known/agent-card.jsonA2A 1.0, JSON-RPC
JSON-endpoint/agent/services.json, beschreven in OpenAPIGewone HTTP
API-catalogus/.well-known/api-catalogRFC 9727, IETF Standards Track

Elk HTML- en markdownantwoord stuurt een Link-header mee die verwijst naar de catalogus, de index met agent skills en beide kaarten, zodat elke pagina naar de rest leidt.

Ontwerpregels die we zouden herhalen

  • Alleen-lezen en openbaar. De MCP-tools declareren readOnlyHint: true en lezen dezelfde gepubliceerde catalogus als de HTML, zonder database erachter. get_project_brief verstuurt, boekt of offreert niets; een mens controleert en verstuurt.
  • Beperkte invoer. Request bodies zijn beperkt tot 8 KiB, Origin-headers van browsers worden gecontroleerd (de MCP-specificatie eist dat) en aanroepen hebben hun eigen rate limit.
  • Geen state. De A2A-agent antwoordt direct, bewaart geen taken, heeft streaming uitgeschakeld en haalt geen bestanden of URL's op die naar hem worden gestuurd.
  • Heldere voorwaarden. /auth.md zegt dat er geen inloggegevens nodig zijn en dat het lezen van openbare data geen toestemming geeft om een bericht te sturen of een betaling te doen.

We hebben ook dingen weggelaten. Readiness-scanners controleren op commerceprotocollen en OAuth discovery. Wij verkopen niets via een checkout en beschermen geen resources, dus die publiceren zou mogelijkheden beschrijven die niet bestaan.

Wie gebruikt deze tools nu: MCP-clients die iemand met /mcp heeft verbonden, en A2A-clients die onze kaart hebben gekregen. Voor een studio is de waarde bescheiden: een nauwkeurig antwoord op "wat doet Dardo, en wat moet ik ze sturen?" Het argument is sterker voor een site met live data waar mensen naar vragen, zoals voorraad, beschikbaarheid of productdocumentatie. Agents die data schrijven hebben authenticatie en controlestappen nodig; dat is AI-automatisering.

WebMCP: dezelfde tools in de browser

WebMCP laat een pagina tools registreren die een AI-agent in de browser kan aanroepen. Het is een Draft Community Group Report van de W3C Web Machine Learning Community Group en stelt zelf dat het geen W3C-standaard is. Volgens web.dev is het in actieve ontwikkeling, kan het veranderen en is het in Chrome uit te proberen via een origin trial.

Onze pagina's registreren dezelfde twee tools via document.modelContext (of navigator.modelContext in oudere previews). Zonder de API voert de browser niets extra's uit. Omdat de tools al bestonden, kostte dit zo'n 40 regels. Zie het als een experiment.

Elke laag, en of het de moeite waard is

LaagWat het isWie het vandaag leestDe moeite waard?
Semantische HTML en formulieren met labelsEchte knoppen, links, landmarks en labelsBrowsers, hulptechnologie en browseragentsJa. Begin hier
robots.txt voor zoek- en user agentsRegels per crawler die zoeken scheiden van trainingOpenAI, Anthropic, Perplexity en Google documenteren hun tokensJa. Test daarna bij de CDN
Content SignalsVoorkeuren voor search, ai-input en ai-train in robots.txtGeen enkel AI-bedrijf dat we controleerden documenteert dat het ze respecteertEén regel. Verwacht niets
Markdown-kopieën met canonical headersEen schone tekstversie van elke paginaAgents die markdown opvragen; er is geen openbare lijst van welkeJa, met de canonical header
llms.txt en llms-full.txtEen samengestelde index en volledige tekst voor agentsGoogle Search negeert het; in geen enkele crawlerdocumentatie staat dat het wordt gelezenHoud het als het gegenereerd wordt. Geen hefboom voor zichtbaarheid
MCP-server (alleen-lezen)Gedeclareerde tools die agents kunnen aanroepenMCP-clients die iemand koppeltAlleen met data of acties die het aanroepen waard zijn
A2A agent cardEen machineleesbare beschrijving van een agentA2A-clients die ernaar verwijzenSpeculatief voor de meeste websites
API-catalogus (RFC 9727)Eén well-known lijst van je openbare API'sTools die ernaar zoekenGoedkoop als je al API's hebt
WebMCPTools die de pagina in de browser registreertChrome, via een origin trialExperiment

Wat we opnieuw zouden bouwen

In volgorde: semantische HTML, geteste crawlertoegang, markdown-kopieën met canonical headers, een gegenereerde llms.txt, en tools alleen als er iets is dat het aanroepen waard is. Meet daarna. Serverlogs laten zien welke agents markdown-kopieën ophalen of /mcp aanroepen. Een fetch is geen vermelding, en niets hiervan garandeert dat een AI-systeem je noemt.

Agent readiness is onderdeel van ons werk aan AI-zoekoptimalisatie, naast de content en metingen die bepalen of AI-antwoorden jou citeren. Wil je dit in je site laten bouwen? Vertel ons over het project.