Skip to content

Tools

What each Tool accepts, returns, changes, and hands off to next.

Your client receives the executable input and output schemas from tools/list. This page adds the choice the wire cannot make for you: when to use each Tool, what changes, and which Tool normally follows.

Every Tool is non-destructive, advertises idempotence, and is limited to this site’s closed world. All but submit_feedback are read-only.

Tool Use it to Effect
list_collections Learn the searchable sections Read-only
list_pages Enumerate pages outside search Read-only
search_content Find posts, terms, and demos Read-only
get_post Resolve one known post slug Read-only
list_tags Learn the site’s subject vocabulary Read-only
get_page_info Read metadata and graph relationships Read-only
get_page_markdown Read what is written at one route Read-only
submit_feedback Record one reviewed message for Colin Write

list_collections

Effect: Read-only.

Use this first when you do not know how the searchable corpus is divided.

  • Input: limit — optional integer, minimum 1. Omit it for the whole set.
  • Result fields: items[].collection, items[].title, items[].path, items[].count, count, and total.
  • Next: pass a returned collection to search_content.
List the collections on lateano.com. Explain what each contains and include its path.

list_pages

Effect: Read-only.

Use this for documentation, About, and index pages that no collection holds and search_content cannot return.

  • Input: limit — optional integer, minimum 1. Omit it for every page.
  • Result fields: items[].path, items[].title, items[].description, count, and total.
  • Next: pass a returned path to get_page_markdown or get_page_info.
List the pages outside the site's searchable collections. Which one explains the API?

search_content

Effect: Read-only.

Use this to search posts, glossary terms, and demos by words, collection, or tag. At least one of those three must describe the question.

  • Input: match — optional { text: string, in: title | body | description | aliases | tags | all }.
  • Input: collection — optional writing | glossary | demos.
  • Input: tag — optional string returned by list_tags.
  • Input: limit — optional integer, minimum 1 and maximum 25. The default limit is 10.
  • Result fields: items[].results[].path, items[].results[].canonical, items[].results[].title, items[].results[].description, items[].results[].collection, items[].results[].date, items[].results[].twin, items[].matched, items[].facets[].facet, items[].facets[].counts[].value, items[].facets[].counts[].count, count, and total.
  • Limit: when matched is larger than the returned rows, narrow the question. There is no next page after the maximum result set.
  • Next: read a result’s path with get_page_markdown.
Search all fields for "caching". Return the strongest matches and say when more matched
than were returned.

get_post

Effect: Read-only.

Use this when you already know a post’s final URL segment. Use search_content when the slug is uncertain.

  • Input: slug — required string.
  • Result fields: items[].results[].path, items[].results[].canonical, items[].results[].title, items[].results[].description, items[].results[].collection, items[].results[].date, items[].results[].twin, items[].matched, items[].facets[].facet, items[].facets[].counts[].value, items[].facets[].counts[].count, count, and total.
  • Next: pass the returned result path to get_page_markdown.
Get the post whose slug is [post-slug], then read it and summarize its main argument.

list_tags

Effect: Read-only.

Use this before tag-filtered search when you need the real slug or want to learn how a subject cuts across collections.

  • Input: limit — optional integer, minimum 1. Omit it for the whole vocabulary.
  • Result fields: items[].slug, items[].title, items[].count, items[].byCollection, count, and total.
  • Next: pass a returned slug to search_content as tag.
List the tags. Find one related to [subject] and show how its documents are split by collection.

get_page_info

Effect: Read-only.

Use this when you know a page route and need metadata or graph relationships rather than its prose.

  • Input: route — required string, such as /glossary or / for the site root.
  • Result fields: page.path, page.canonical, page.title, page.description, page.indexing, page.collection, page.date, page.tags[], page.aliases[], page.twin, page.outgoingReferences[].path, page.outgoingReferences[].title, page.referencingPosts[].path, page.referencingPosts[].title, page.related[].path, and page.related[].title.
  • Next: follow a returned path, or read the page with get_page_markdown.
Get the page information for [route]. Group its outgoing references, referencing posts,
and related pages.

get_page_markdown

Effect: Read-only.

Use this to read a page after another Tool returns its route.

  • Input: route — required string, including / for the site root.
  • Result: plain Markdown text. When the page publishes a Markdown address, the result also carries that address as a resource link.
  • Limit: a long page is cut. The result says where it stopped and links the complete published document; no Tool returns the remainder.
  • Next: answer from the text, or use get_page_info for relationships.
Read [route] as Markdown. Separate claims made by the page from your own inference.

submit_feedback

Effect: Write.

Use this only after the user has reviewed the message. It records feedback for Colin; it does not edit the site or return a reply.

  • Input: idempotency_key — required string (uuid).
  • Input: message — required string.
  • Input: kind — required missing | broken | confusing | inaccurate | other.
  • Input: severity — required high | medium | low.
  • Input: about — optional string route.
  • Result fields: about and receivedAt.
  • Retry: reuse the same UUID only for the same submission. Generate a new UUID when the message, kind, severity, or route changes.
  • Next: report what was recorded and when. No Tool reads the private message back.
Draft feedback about [route]: [message]. Classify its kind and severity, show the exact
submission, and wait for my approval before sending it.
---
title: "Tools"
description: "What each Tool accepts, returns, changes, and hands off to next."
url: "https://lateano.com/developers/mcp/tools"
author: "Colin Lateano"
---

# Tools

What each Tool accepts, returns, changes, and hands off to next.

Your client receives the executable input and output schemas from `tools/list`.
This page adds the choice the wire cannot make for you: when to use each Tool,
what changes, and which Tool normally follows.

Every Tool is non-destructive, advertises idempotence, and is limited to this
site's closed world. All but `submit_feedback` are read-only.

| Tool                | Use it to                             | Effect    |
| :------------------ | :------------------------------------ | :-------- |
| `list_collections`  | Learn the searchable sections         | Read-only |
| `list_pages`        | Enumerate pages outside search        | Read-only |
| `search_content`    | Find posts, terms, and demos          | Read-only |
| `get_post`          | Resolve one known post slug           | Read-only |
| `list_tags`         | Learn the site's subject vocabulary   | Read-only |
| `get_page_info`     | Read metadata and graph relationships | Read-only |
| `get_page_markdown` | Read what is written at one route     | Read-only |
| `submit_feedback`   | Record one reviewed message for Colin | Write     |

## `list_collections`

**Effect:** Read-only.

Use this first when you do not know how the searchable corpus is divided.

- **Input:** `limit` — optional `integer`, minimum 1. Omit it for the whole set.
- **Result fields:** `items[].collection`, `items[].title`, `items[].path`,
  `items[].count`, `count`, and `total`.
- **Next:** pass a returned `collection` to `search_content`.

```text
List the collections on lateano.com. Explain what each contains and include its path.
```

## `list_pages`

**Effect:** Read-only.

Use this for documentation, About, and index pages that no collection holds and
`search_content` cannot return.

- **Input:** `limit` — optional `integer`, minimum 1. Omit it for every page.
- **Result fields:** `items[].path`, `items[].title`, `items[].description`,
  `count`, and `total`.
- **Next:** pass a returned `path` to `get_page_markdown` or `get_page_info`.

```text
List the pages outside the site's searchable collections. Which one explains the API?
```

## `search_content`

**Effect:** Read-only.

Use this to search posts, glossary terms, and demos by words, collection, or tag.
At least one of those three must describe the question.

- **Input:** `match` — optional
  `{ text: string, in: title | body | description | aliases | tags | all }`.
- **Input:** `collection` — optional `writing | glossary | demos`.
- **Input:** `tag` — optional `string` returned by `list_tags`.
- **Input:** `limit` — optional `integer`, minimum 1 and maximum 25. The default
  limit is 10.
- **Result fields:** `items[].results[].path`, `items[].results[].canonical`,
  `items[].results[].title`, `items[].results[].description`,
  `items[].results[].collection`, `items[].results[].date`,
  `items[].results[].twin`, `items[].matched`, `items[].facets[].facet`,
  `items[].facets[].counts[].value`, `items[].facets[].counts[].count`, `count`,
  and `total`.
- **Limit:** when `matched` is larger than the returned rows, narrow the question.
  There is no next page after the maximum result set.
- **Next:** read a result's `path` with `get_page_markdown`.

```text
Search all fields for "caching". Return the strongest matches and say when more matched
than were returned.
```

## `get_post`

**Effect:** Read-only.

Use this when you already know a post's final URL segment. Use `search_content`
when the slug is uncertain.

- **Input:** `slug` — required `string`.
- **Result fields:** `items[].results[].path`, `items[].results[].canonical`,
  `items[].results[].title`, `items[].results[].description`,
  `items[].results[].collection`, `items[].results[].date`,
  `items[].results[].twin`, `items[].matched`, `items[].facets[].facet`,
  `items[].facets[].counts[].value`, `items[].facets[].counts[].count`, `count`,
  and `total`.
- **Next:** pass the returned result `path` to `get_page_markdown`.

```text
Get the post whose slug is [post-slug], then read it and summarize its main argument.
```

## `list_tags`

**Effect:** Read-only.

Use this before tag-filtered search when you need the real slug or want to learn
how a subject cuts across collections.

- **Input:** `limit` — optional `integer`, minimum 1. Omit it for the whole
  vocabulary.
- **Result fields:** `items[].slug`, `items[].title`, `items[].count`,
  `items[].byCollection`, `count`, and `total`.
- **Next:** pass a returned `slug` to `search_content` as `tag`.

```text
List the tags. Find one related to [subject] and show how its documents are split by collection.
```

## `get_page_info`

**Effect:** Read-only.

Use this when you know a page route and need metadata or graph relationships
rather than its prose.

- **Input:** `route` — required `string`, such as `/glossary` or `/` for the site
  root.
- **Result fields:** `page.path`, `page.canonical`, `page.title`,
  `page.description`, `page.indexing`, `page.collection`, `page.date`,
  `page.tags[]`, `page.aliases[]`, `page.twin`,
  `page.outgoingReferences[].path`, `page.outgoingReferences[].title`,
  `page.referencingPosts[].path`, `page.referencingPosts[].title`,
  `page.related[].path`, and `page.related[].title`.
- **Next:** follow a returned path, or read the page with `get_page_markdown`.

```text
Get the page information for [route]. Group its outgoing references, referencing posts,
and related pages.
```

## `get_page_markdown`

**Effect:** Read-only.

Use this to read a page after another Tool returns its route.

- **Input:** `route` — required `string`, including `/` for the site root.
- **Result:** plain Markdown text. When the page publishes a Markdown address, the
  result also carries that address as a resource link.
- **Limit:** a long page is cut. The result says where it stopped and links the
  complete published document; no Tool returns the remainder.
- **Next:** answer from the text, or use `get_page_info` for relationships.

```text
Read [route] as Markdown. Separate claims made by the page from your own inference.
```

## `submit_feedback`

**Effect:** Write.

Use this only after the user has reviewed the message. It records feedback for
Colin; it does not edit the site or return a reply.

- **Input:** `idempotency_key` — required `string (uuid)`.
- **Input:** `message` — required `string`.
- **Input:** `kind` — required `missing | broken | confusing | inaccurate | other`.
- **Input:** `severity` — required `high | medium | low`.
- **Input:** `about` — optional `string` route.
- **Result fields:** `about` and `receivedAt`.
- **Retry:** reuse the same UUID only for the same submission. Generate a new UUID
  when the message, kind, severity, or route changes.
- **Next:** report what was recorded and when. No Tool reads the private message back.

```text
Draft feedback about [route]: [message]. Classify its kind and severity, show the exact
submission, and wait for my approval before sending it.
```