Add search to your docs #
Prompt:
Add search to our docs. Write a small search service for the sidebar's search box.
Also works: "Connect our docs search box to Algolia." "Our docs search box says search is not available."
The tool draws the search box, but it does not search by itself. The box sends the reader's words to an address you choose and shows what comes back. Your AI coding tool can write the service at that address in a few dozen lines. It reads the pages from the files every build writes (step 1), answers in the form the box reads (step 2), and is named in the config file (step 3).
What your tool does #
- Builds a word index of the pages from the build's own files, when the site is built or deployed.
- Writes one web route that takes the reader's words and answers with the best-matching pages.
- Names that route's address in the config file and rebuilds the site.
- Or, if you already use a search service, writes a small route that asks that service and passes its answer on in the box's form.
What you need #
- A place that can run a small web route: the server that already serves your site, or any hosting that runs code.
- A site built from a config file (Build one site for several products). The box appears only on a site build.
Before your AI starts #
This section is for your AI coding tool: what it checks and gathers before it begins. You don't need to do these steps yourself.
- The site builds and passes its check.
- It knows where the built folder is served from, so the route can read the build's files or be given them at deploy.
Steps #
1. Read the pages from the build #
Every product's tree holds the files a search needs (Machine files):
docs.jsonlists every page with its route, title, description, and headings with their anchors.- Each page's Markdown copy,
index.mdbeside itsindex.html, holds the page's text. llms-full.txtholds every page's text in one file, if one read is simpler.
Index the words of each page, or of each section under a heading. A title or heading word usually counts for more than a body word. A ranking such as BM25 is a common choice and needs no other service.
Leave out what some readers may not see. If the site marks a product as gated, search its pages only for a reader allowed to see that product, or not at all.
2. Answer the box #
The box sends a GET request with the reader's words as q, such as /search?q=deploy+app. If your service expects another name, such as query, set it as searchParameter in the config file (step 3). Answer with JSON: an object holding a list as hits, best match first. Each hit has these members (The search box has the full rules):
| Member | Required | Contains |
|---|---|---|
tree |
yes | The product's tree word from the config file, such as cloud. |
title |
yes | The page's title. |
route |
yes | The page's address on the same host, starting with one /. Write a plain path: the box leaves out a route that the browser reads as another host. |
heading |
no | The section's heading, where the hit is a section. |
anchor |
no | The section's anchor from docs.json. |
excerpt |
no | A short line of the matching text. |
Return eight hits or fewer. The box shows at most eight and sets every text as plain text.
A short answer looks like this:
{
"hits": [
{
"tree": "cloud",
"title": "Store a secret",
"route": "/cloud/getting-started/store-a-secret/",
"heading": "Store the key",
"anchor": "store-the-key",
"excerpt": "Store an API key by name, and call its API through the gateway."
}
]
}
If the route runs on another host than the pages, it must allow the pages' origin to read its answer, with the header Access-Control-Allow-Origin. A limit on requests from one address keeps the route cheap. The box waits until the reader pauses, so a person sends few requests.
3. Name the address in the config file #
Put the route's address in the config file as search, then rebuild:
{
"products": [
{ "label": "Backend & Hosting", "name": "Turn Zero Cloud", "source": "cloud-docs", "base": "/cloud" }
],
"search": "/search"
}
The address starts with / for a route on the same host, or with https:// for another host.
To send the words in another parameter than q, add "searchParameter": "query", or the name your service expects. It is a short word: a letter, then up to 31 letters, digits, -, or _.
4. Or connect a search service you already use #
A hosted search service answers in its own form. Write a small route at the site's search address that asks the service with the reader's words and returns the hits in the form of step 2. Feed the service the pages from the files of step 1 whenever the site is built.
5. Try it #
Open a page of the built site, type a word that appears in one page's title, and pause. That page should be listed first. A word that appears nowhere should show No pages match.
Expected result #
The search box lists matching pages as the reader types, each under its product's heading, and each hit opens the page at its section.
Refusals #
The box shows one of two lines in place of hits:
| What the box shows | Cause | Remedy |
|---|---|---|
Search is not available right now. |
The request failed, or the answer was not JSON. | Check that the route answers at the address in the config file, and that it allows the pages' origin if it is on another host. |
No pages match. |
The answer held no hits, or every hit's route was not a path on the same host. | Check the index holds the pages, and that each route starts with one /. |
Related #
- The search box states every rule the box follows.
- Build one site for several products writes the config file the search address goes in.
- Build for AI tools describes the machine files the index reads.