Skip to main content
Glama

open-mcp-apps

CI npm license node MCP Registry

English | 简体中文

Give your AI a persistent, reusable UI. It builds the app once — you keep it forever.

open-mcp-apps is an open engine built on MCP Apps (ui://, io.modelcontextprotocol/ui) — an extension to the core Model Context Protocol specification, and the first official one, live since 26 January 2026. It gives any MCP-Apps-capable host (Claude Desktop, claude.ai, Codex, ChatGPT, …) three things the extension itself doesn't provide:

  1. An app registry the AI can write to. Ask for a UI that doesn't exist — the AI reads the authoring guide, writes a single-file HTML app against a tiny window.oma API, and saves it. From that moment you can open it by name, in this chat and every future one.

  2. Persistent, versioned data — separate from the UI. Apps bind to generic collections of items backed by SQLite plus an append-only change_event ledger. Every mutation is an idempotent domain command (command_id) with optimistic concurrency (expected_version). The AI and the human edit the same store — the widget is just a view.

  3. A shell runtime so AI-written apps actually work. Serving ui://, the engine wraps the app with the official MCP App bridge, host theming (Claude's design tokens, light/dark), and the window.oma data API. What you write is a view; the protocol, persistence, idempotency and theming are the engine's problem.

Which of those hosts this engine reaches. It runs on your machine and binds 127.0.0.1, so it serves the hosts on that same machine: Claude Desktop, Claude Code, Codex, plus its own browser viewer. A browser host cannot reach a loopback server on your laptop, so claude.ai and ChatGPT web need a remote deployment — today that means the hosted openmcp.app, which runs this same engine for you. Running that remote shape yourself is on the roadmap and not done.

Version

0.7.0 (CHANGELOG.md)

License

MIT, whole repository (LICENSE · LICENSING.md)

npm

@2nd1st/open-mcp-appsscoped; the unscoped name is an unrelated package

Command

npx -y @2nd1st/open-mcp-apps — the line your host's MCP config runs; a stdio server, not something to run by hand (typed into a terminal it just waits, and says so)

Requires

Node 22 or newer. git too, on the installer path

Surface

33 tools · a built-in App Store · 3 system apps seeded

Platforms

macOS · Windows · Linux

Hosts

Claude Desktop · Claude Code · Codex · ChatGPT web — see Host support

Hosted

openmcp.app — the remote shape, and the way to reach browser hosts (claude.ai, ChatGPT)

Install

open-mcp-apps runs as a local MCP server. First get it connected to your host (below); then onboarding happens inside the host, separately — that's where the AI builds your first app.

From npm — nothing to clone

If you are comfortable editing your host's config file, point it at the published package and let npx fetch the engine. This path needs only Node 22 — no git, and no checkout for you to keep updated. Paste this into your host's MCP server config:

{
  "mcpServers": {
    "open-mcp-apps": {
      "command": "npx",
      "args": ["-y", "@2nd1st/open-mcp-apps"]
    }
  }
}

Two things the installer below does that this path does not: it registers the server into every host it finds, and it pre-seeds the built-in system apps (settings, dashboard, App Store) into your store — so on the npx path your registry starts empty and your AI installs what it needs from the App Store on demand, which is fully available either way. Your data lives in the same fixed per-user store, so you can move between an npx server and a cloned one without migrating anything.

A note on npm: this project publishes under the scoped name @2nd1st/open-mcp-apps. The unscoped open-mcp-apps on the registry is not this project — that name is held by an unrelated package. Check for the @2nd1st/ prefix; the scope is the only thing telling the two apart.

With the installer — one command

Installing needs a shell, so the chat apps (Claude Desktop, Codex) can't install themselves — use one of these instead:

curl -fsSL https://raw.githubusercontent.com/2nd1st/open-mcp-apps/main/install.sh | sh

It opens a short picker to choose which hosts to register into — Claude Desktop, Claude Code, Codex — plus your permission preference. Skip it with -s -- --yes, or target one host with -s -- --host codex.

Where it puts the clone, before you pipe anything into a shell: ~/open-mcp-apps. Set OMA_DIR to put it somewhere else — curl -fsSL <url> | OMA_DIR=~/src/oma sh. Re-running the one-liner updates that same clone in place instead of making a second one. Your apps and data are not in it (they live in the per-user store under Configuration), so the folder is safe to move or delete — and node uninstall.mjs does not delete it for you.

With a coding agent (Claude Code, Codex CLI — they have a shell), paste:

Read https://raw.githubusercontent.com/2nd1st/open-mcp-apps/main/install.md and follow it.

Either way, install.mjs registers the server into each host you pick, idempotently — it never clobbers your other servers, pins a stable node launcher (native SQLite ABI), reports what changed, and cleans up a pre-rename entry if one lingers. Your data lives in a fixed per-user store (not inside the clone), so every host shares the same apps and data.

From a clone — for development

git clone https://github.com/2nd1st/open-mcp-apps && cd open-mcp-apps
npm install
node install.mjs        # same picker as the one-liner above

To wire a clone into a host by hand instead, point it at the checkout — this is the shape install.mjs writes:

{
  "mcpServers": {
    "open-mcp-apps": {
      "command": "node",
      "args": ["/absolute/path/to/open-mcp-apps/src/server.mjs"]
    }
  }
}

Hosted

openmcp.app runs the engine for you. The engine in this repository binds 127.0.0.1 by design, so a self-hosted remote deployment is not a supported shape yet — see Status and roadmap.

Uninstall

node uninstall.mjs unregisters the server from every host it finds — but keeps your data: the shared store stays put, so re-installing later restores every app and all data. It also leaves the installer's clone (~/open-mcp-apps, or wherever OMA_DIR pointed) on disk — nothing here ever deletes that folder, so remove it yourself when you want the checkout gone.

node uninstall.mjs           # unregister from all detected hosts — keeps your data
node uninstall.mjs --purge   # also delete the shared store (apps + data), irreversible
node uninstall.mjs --check   # read-only: show what's registered and what would change

Related MCP server: AI PC Assistant MCP Server

Requirements

  • Node 22 or newer, on macOS, Windows or Linux.

  • git — only on the installer path. The npx path above needs neither git nor a checkout. The installer checks for both and stops with a message rather than half-installing if either is missing.

  • A host that renders ui:// if you want widgets in the conversation. Terminal hosts (Claude Code in a terminal, codex CLI) drive the same data by design and put the UI on a browser screen beside the terminal instead — one that can follow along, showing whatever the AI just opened. The per-host detail is in Host support.

  • After installing or updating, fully quit and reopen the host (Cmd-Q, not just closing the window) — it keeps its old server process on the old data until fully quit.

Configuration

Every setting is an environment variable, set in the env block of your host's MCP server entry:

{
  "mcpServers": {
    "open-mcp-apps": {
      "command": "npx",
      "args": ["-y", "@2nd1st/open-mcp-apps"],
      "env": {
        "OMA_VIEWER": "1",
        "PORT": "8787",
        "OMA_DYNAMIC_TOOLS": "0"
      }
    }
  }
}

Variable

Default

What it does

OMA_VIEWER

1

The browser viewer on loopback. 0 doesn't start it at all.

PORT

8787

Where the viewer listens.

OMA_DYNAMIC_TOOLS

0

1 also publishes one open_<name> tool per saved app. Off by default because it costs prompt cache — and one approval prompt per app.

OMA_DB

per-user store

Path to the SQLite store. Set it to isolate a store.

Where your data lives. The whole store is one SQLite file, open-mcp-apps.db, in ~/Library/Application Support/open-mcp-apps/ (macOS), %APPDATA%\open-mcp-apps\ (Windows), or $XDG_DATA_HOME else ~/.local/share/open-mcp-apps/ (Linux). It is outside any clone, which is why every host shares the same apps and data.

First-run permissions. The first few tool calls each show an approval dialog — pick "Always allow". The tool set is small and stable on purpose: read-only tools generally skip approval, and the single open_app tool covers opening every app (including ones the AI creates later) behind that one grant, so nothing new asks again — on every host the installer registers, with no exceptions any more. From 2026-07-28 to 2026-08-16 there were two: Claude Desktop and Claude Code were registered with OMA_DYNAMIC_TOOLS=1, which routed around a chat-surface bridge regression by giving every app its own open_<name> tool, at one approval prompt per app. Re-measured on Desktop 1.30096.5, that symptom is gone, so the installer no longer sets the flag for anybody — KNOWN-ISSUES.md carries both readings. If you installed during that window, your entry still has the flag: node install.mjs --check reports it as stale, and re-running the installer removes that one key while leaving every other env value you have set exactly where it is. You can also batch approvals in Settings → Connectors → open-mcp-apps → Tool permissions.

Usage

Start in your host. Restart it after installing. New here? The engine ships one MCP prompt, get_started. A host that surfaces prompts lists it as Get started with open-mcp-apps; hosts that render prompts as slash commands spell it /mcp__open-mcp-apps__get_started. Picking it hands the AI the whole opening move. Not every host surfaces prompts — where yours doesn't, nothing is lost, because the prompt is just a sentence you can say yourself: "I just installed open-mcp-apps — show me how to use it with a couple of examples, and suggest a few apps that fit how I work." Either way it looks at what you already have and what the App Store already offers, asks you a couple of questions, and sets up a first app tailored to you. This step is separate from install and lives in the host. Or just ask directly:

  • "make me a board for what I'm juggling right now" → the AI writes it, seeds it, and opens it (persistent)

  • "make me a habit tracker" → watch it read the guide, write the app, save it, open it

  • close the app, reopen, ask again → everything is still there

The loop

"make me a kanban"
      │
      ▼
list_apps ── exists? ──► open_app {app: "kanban"}     (reuse, instant)
      │ no
      ▼
get_app_guide ──► AI writes HTML ──► save_app
      │
      ▼
open_app {app: "kanban"}  →  rendered inline, themed, persistent — reusable in every future chat

Apps accumulate. Each one is single-purpose and independent — a board, a tracker, a splitter — minted for the task in front of you and kept for the next time you need it.

What it looks like

Apps render inline, in the chat you were already having. Ask for one and the AI writes it:

Codex — asking for a reading tracker; the AI writes it and it renders inline, already holding the three books

Come back in another chat — or another host — and it's still there, with your data in it:

Claude — a new chat opens the same reading list, now eight books long

The built-in App Store — rebuilt in 0.5.0 as a real storefront — ships 22 ready-made apps, with working previews and one-click install:

The App Store — live previews of ready-made apps

Companion — an AI character with shared memory

Family Week — dinners, chores rotation, shopping and weekend plans

Study Cards — spaced repetition with review heatmap and deck shelf

Knowledge Cards — a visual library of saved answers

Every app above is a single HTML file bound to plain data collections — written with the same window.oma API and authoring guide your AI will use for the apps it builds you.

Multiple widgets in one conversation work fine (habit-streaks + meal-planner side by side).

The browser viewer, and the port it binds

Every install runs a small local web server on http://127.0.0.1:8787. It is how you see your apps outside a chat window — one page per app, the same data your AI is reading — and in a terminal host it is the only way to see them at all, so the AI hands you the link when it builds or opens something.

It starts on its own; OMA_VIEWER and PORT above change that. If the port is already taken by another open-mcp-apps process, that one is already serving the same data and this one just shares its address; if it is taken by something else, you get no viewer and no links rather than a link into a stranger's server.

There is no password on it, and that is deliberate. The listener is hard-wired to 127.0.0.1, so there is no setting that makes it answer from another machine. Any program on your computer that could reach the port can already open the SQLite file directly — a password would be a lock beside an open wall. The one way this reaches the internet is a tunnel you start yourself, which is its own deliberate decision; while a tunnel is up, treat its URL as a secret, because it is currently the only thing standing between the internet and your data.

Host support

Live-tested 2026-07-22; ChatGPT web row updated 2026-07-28. Both readings predate 0.5.0 — the largest change so far, and later than either date. Apart from the cells that carry their own 2026-08-16 date, nothing in this table has been re-tested on 0.5.0 or newer; a date says when that row was true, not that it was checked again since.

Host

Renders widgets

Human clicks widget

AI operates data

Same store

Claude Desktop (local stdio)

✅ — re-checked 2026-08-16 on 1.30096.5: the universal open_app renders in chat without the OMA_DYNAMIC_TOOLS workaround that shipped for 1.24012.9 (see KNOWN-ISSUES)

✅ full loop incl. sendMessage reply

Browser viewer (/view/<name>)

✅ (no chat attached — sendMessage degrades to a notice)

via CLI AI

Codex desktop (ChatGPT app, enable_mcp_apps flag) — tested against a local engine; remote not established

✅ experimental

◐ updates/toggles from widget clicks work; adds were blocked host-side. The umbrella request openai/codex#28912 (an enhancement: "make MCP apps work end-to-end in the Codex GUI") closed as completed on 2026-08-05 — but #30092, the bug matching this exact failure and reproduced there by a third party, was still open on 2026-08-16. Not re-tested here either way, so the cell stays ◐. See KNOWN-ISSUES

Claude Code — in a terminal (claude mcp)

— in the chat, by design (text fallback) — but see a screen beside the terminal

— in the chat

Claude Code — the Code surface inside the Claude app

✅ live-tested 2026-08-16: an app opened with the universal open_app renders inline, the same shape the chat surface gives

not measured on this surface

codex CLI / IDE

— in the chat, by design (text fallback) — but see a screen beside the terminal

— in the chat

ChatGPT web (Work mode)

✅ live-tested 2026-07-28 (remote HTTPS) — renders at full height, no clamping; a widget loses its data after a page refresh (mitigation shipped, awaiting live re-test here — see KNOWN-ISSUES)

✅ a widget button added a row and it stuck

Everything rides the MCP Apps bridge, so host fixes upstream (e.g. #28912) benefit this project with zero changes.

On Claude Code specifically: it is one product with two surfaces, and only one of them can draw — which is why it takes two rows. In a terminal there is no inline widget surface at all: that is architecture rather than a gap, and it is exactly what a screen beside the terminal is for. The Code surface inside the Claude app has a UI and renders inline; the 2026-08-16 reading there came through the universal open_app.

On Codex specifically: plugins are registered on the web side, so a locally-installed engine is reached as an MCP server, not as a plugin — which is the right path for a self-hosted install anyway. Widget rendering in the ChatGPT desktop app also appears to depend on how you are signed in (we have seen it work under an account sign-in; not yet established under an API key).

A screen beside the terminal

Those two cells say the chat shows text. They do not say there is no UI. Since 0.5.1 the engine remembers which app was opened last and pushes that pointer to the viewer on the /events frame, and an app can place a region — oma.embed("@live", {into}) — that mounts whatever the AI opened last and swaps itself when the AI opens another. The App Store ships one: install live, open http://127.0.0.1:8787/view/live in a window you then leave alone, and the terminal keeps the conversation while that screen shows the app. The AI opens or writes from the CLI, the screen follows, and you can click, edit and type into it there. Headless CLI use is what it was built for.

The cheapest form of "that screen" is a browser pane in the same tiled workspace — one column over from the agent, in the window you are already working in. Same machine, no tunnel, no second device; most modern terminal setups can put a browser next to a shell, and that is all this needs. A second monitor is the same idea with more desk, and a screen on another device is the same idea again with the caveat below.

The costs are real and worth stating plainly. There is still no widget in the transcript. sendMessage degrades to a notice on a standalone page, exactly as in the Browser viewer row — clicks change data, they do not talk back to the chat. The viewer has to be running (OMA_VIEWER, on by default) with a browser pointed at it; this is not zero-config. And the listener is bound to 127.0.0.1, so "a spare tablet on the wall" means this machine's screen unless you put up the tunnel described above and accept what that section says about it. Inside a chat host the same region deliberately draws a placeholder instead of following anything.

Described from the code as built, not measured on a host — the live-test dates above cover the table, not this section.

Writing an app yourself

The AI is the usual author, but it isn't the only one — its context window shouldn't be the ceiling on what an app can be. Build one in your own editor, with your own bundler, and install it:

node install-app.mjs ./my-app.html              # yours, full trust — same as an AI-authored app
node install-app.mjs ./my-app.html --sandboxed  # untrusted: runs behind the runner, no capabilities
node install-app.mjs --list                     # what's installed, and under whose provenance

# a build pipeline's output: a readable template + its bundle, plus the declaration as its own file
node install-app.mjs ./ui.html --name my-app --manifest ./manifest.json \
  --asset ./dist/app.js --asset ./dist/app.css --update

Two shapes are accepted. One self-contained HTML document — no size cap (keep it lean: data lives in the collection, source is read in windows) — the engine injects the kit CSS, the host's design tokens and window.oma. Or a template plus a bundle: the HTML is a readable mount point that references its own build output (<script type="module" src="oma-asset:app.js">, <link rel="stylesheet" href="oma-asset:app.css">), --asset pushes those files into the app's file plane, and the engine inlines them the moment the document leaves the store — a widget's CSP allows no external subresource, and a host iframe could not reach this machine anyway.

The trade: the AI can no longer iterate on it — your files are the source of truth, you rebuild and re-install. It can still read a single-document app's source; for a template + bundle app it reads the template and the bundle stays yours (edit_app and the AI's save_app refuse with built_outside; re-running the command above is the edit). Either way the app shares your data like any other. Provenance is not overwritable in either direction, so an app installed --sandboxed stays sandboxed until you delete it. What a widget may connect to is the app's own declaration (manifest.csp, relayed to the host per the MCP Apps spec — nothing by default), and an app's functions run engine-side and may fetch — see RUNTIME.md §5.1 and §6.1, and the two type files for what an app sees — @2nd1st/open-mcp-apps/types/window-oma (the window.oma API) and @2nd1st/open-mcp-apps/types/oma-function (the args/api a function body gets) — both resolve through the package exports.

RUNTIME.md is the contract — the window.oma API in both modes, what a sandboxed app can still do, and the traps that only bite authors who aren't the AI. It carries a version (oma.contract) and test/runtime-contract.mjs pins it to the two runtimes' real surfaces, so it can't drift from them silently.

Security model

Trust is tiered by where an app came from. Locally-authored and system apps run in direct mode. The engine also ships a runner — a sandboxed srcdoc iframe with a CSP-first document and a minimal read-scoped bridge — as the mandatory execution mode for any app that isn't locally trusted, plus reserved security:* / policy:* config keys that generic data writes can't touch and an out-of-band privileged writer.

Honest status: everything in the OSS version — your apps, AI-built apps, and the built-in App Store apps (all first-party) — runs locally in direct mode with full trust; there is nothing third-party to sandbox yet. The runner is built and tested but dormant: it is the ready seam for shared/published apps later, where review + sandboxing arrive together. See SECURITY.md for the full threat model and trust tiers.

Design positions (why it's built this way)

  • UI and data persist separately, both versioned. Apps are views; collections are truth; the ledger is history. Swap either without losing the other.

  • The AI talks domain commands, never SQL, never raw state. That's what makes human+AI concurrent editing safe (idempotency + optimistic concurrency at the command layer).

  • Extension-first. Everything rides the MCP Apps bridge — no host-private APIs. One codebase should serve every host that renders ui://.

  • Single-purpose, not composite. Each app owns one scenario and its own collection; the engine mints a new one rather than cramming features into an old one. System apps (settings, dashboard) are the deliberate exception — engine-owned, privileged, allowed to see across collections.

Troubleshooting

Symptom

What it is

Updated, but the host still shows the old behaviour

The host keeps its old server process on the old data until fully quit (Cmd-Q, not just closing the window).

Approval dialogs came back after a Claude Desktop auto-update

A Desktop auto-update occasionally resets these decisions (upstream #56954, closed 2026-06-23 as not planned) — no fix is coming from that issue, so just re-allow.

One approval prompt per app

OMA_DYNAMIC_TOOLS=1 is in your host entry — either you put it there, or you installed between 2026-07-28 and 2026-08-16, when the installer set it for Claude Desktop and Claude Code as a workaround. node install.mjs --check calls such an entry stale; re-running the installer removes that one key and keeps the rest of your env. See Configuration.

No viewer link, or the viewer is somebody else's

The port is taken by a non-open-mcp-apps process. Set PORT to something free.

A widget loses its data after a page refresh (ChatGPT web)

Known, mitigation shipped, live re-test pending — KNOWN-ISSUES.md.

Widget clicks can update but not add (Codex desktop)

Blocked host-side. The umbrella request openai/codex#28912 closed as completed on 2026-08-05, but that one is an enhancement, not this defect: the matching bug, #30092, was still open on 2026-08-16. Update Codex and try, but expect it to still bite.

You want to start completely clean

Fully quit your host(s), delete open-mcp-apps.db (plus its -wal/-shm siblings) from the store directory under Configuration. All apps and data gone, irreversibly, while staying installed.

pnpm install exits 1 with ERR_PNPM_IGNORED_BUILDS

pnpm 11 refuses third-party build scripts until you decide about them, and calls that an error. Nothing here needs building — better-sqlite3 loads a prebuilt binary it ships, and esbuild's binary comes from its platform package — so the tree it leaves behind is complete and working. Answer pnpm approve-builds however you like, or use npm. We do not declare those scripts as allowed, because that would make pnpm compile better-sqlite3 on machines with no toolchain (a container, most CI) and fail there for nothing.

Development

src/server.mjs

stdio MCP server; single open_app path (per-app open_<name> tools off unless OMA_DYNAMIC_TOOLS=1)

src/http.mjs

/mcp (stateless Streamable HTTP) + /view/<name> browser viewer, bound to 127.0.0.1

src/store.mjs

SQLite: items + app registry + change_event ledger (idempotent, OCC)

src/shell-runtime.js

browser runtime injected into every app (window.oma)

src/shell.mjs

wraps stored HTML with runtime + design-token fallbacks at serve time

src/guide.mjs

the authoring contract the AI reads before generating an app

install-app.mjs

install an app you wrote yourself, from a file — the one door into the registry that doesn't go through the AI

components/

3 system apps installed on seed (settings, dashboard, app-store) + 22 App Store apps — not auto-installed; browse the app-store app for live previews with sample data and one-click install

npm test                     # every suite below, plus the static invariants and budget checks
node test/server-smoke.mjs   # 453 assertions over real stdio — incl. runtime app creation
node test/http-smoke.mjs     #  81 assertions over the HTTP transport (incl. SSE /events, viewer)
node test/provenance.mjs     #  39 assertions that an app's author — its trust tier — is not overwritable
node test/seed-smoke.mjs     #  22 assertions on the seed / design-kit pipeline
node test/files-smoke.mjs    #  41 assertions on the per-app file store (chunked uploads, GC races)

Contributions need nothing signed — MIT in, MIT out (CONTRIBUTING.md).

Status and roadmap

Early v0 — proven end-to-end on Claude Desktop; cross-vendor render + shared store proven on Codex desktop and the browser viewer.

What 0.5.0 changed (breaking, and the largest change so far — CHANGELOG.md has the full account):

  • An app's declaration is a first-class object. save_app takes ui and manifest as two slots instead of a manifest block buried in the document, and every revision snapshots both, so restoring brings back the pair.

  • An app can expose a function — a data→data closure the AI calls with call_function, run by the engine against that app's own collections. The seat is opt-in at createEngine and absent by default, so a hosted deployment cannot inherit it.

  • Deleting a row is confirmed by the engine, inside the store transaction every path passes through. App authors no longer write confirmation UI; the apps that carried their own arm-then-delete had it removed.

  • promote_app turns a one-off visual into a kept app in one atomic step, and edit_app takes a hash-checked {offset, length} range, so a model that has read a window can edit it without sending an anchor back up.

  • Settings and the App Store were rebuilt — rail navigation, in-place detail pages, and the storefront pictured above.

  • Underneath: SDK v1 → v2, 2026-07-28 in the supported protocol versions, and a tool surface audited down to 33 tools. Renamed and removed tools mean hosts will ask you to approve the tools once more after upgrading.

Where it stands:

  • engine: registry + shell + generic data commands + ledger

  • system apps installed (settings, dashboard, app-store); 22 App Store apps with live previews, one-click install

  • AI app creation loop (guide → save → open)

  • in-context onboarding (ask how to use it → the AI reads your history/memory and builds a tailored starter set)

  • security foundation: trust tiers + sandboxed runner + reserved config keys

  • multi-host discovery installer (Claude Desktop · Claude Code · Codex) + shared per-user store

  • npx one-command install (@2nd1st/open-mcp-apps on npm)

  • self-hosted remote (Streamable HTTP) as a supported shape → claude.ai / ChatGPT / mobile off an engine you run — the transport exists (src/http.mjs) and has been live-tested over HTTPS; what's missing is the hosted story, since the engine binds 127.0.0.1 by design. Those browser hosts already work against the hosted openmcp.app; this box is about doing it yourself

  • one-click install with no shell

  • app export/import → sharing → community App Store (review + runner sandbox activate here)

License

MIT, for the whole repository — the engine and the apps in components/ alike (LICENSE · LICENSING.md). Use it, fork it, modify it, embed it, run a modified version as a hosted service; keep the copyright notice with substantial portions you redistribute. That is the whole obligation. Up to v0.5.2 the engine was AGPL-3.0-only under a directory split — see LICENSING.md for what changed and why.

The names open-mcp-apps, openmcp.app, SecondFirst, and 2nd1st, and their logos, are not granted by the license — see TRADEMARKS.md. Fork the code freely; give your fork its own name.

Copyright © 2026 2nd1st.

© 2026 2nd1st

Available Tools

33 tools
app_historyApp history (checkpoints)A
Read-only

List an app's checkpoints as {checkpoint, ts, ui_size} — metadata only, NEVER the source (keeps context small; use get_app for the current source). Checkpoint 1 is the oldest; restore_app takes that number. History survives delete_app (tombstone). Each checkpoint snapshots BOTH slots (ui + manifest); restore brings back the pair.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameYes

Output Schema

ParametersJSON Schema
NameRequiredDescription
nameYes
historyYes

TDQS

A4.9/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the annotations (readOnlyHint, openWorldHint), the description discloses that the tool returns metadata only, not source, which is a deliberate design to keep context small. It also uncovers tombstone semantics (survives delete_app) and that each checkpoint snapshots both UI and manifest, providing restoration context.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is three sentences, each adding distinct value: listing action, checkpoint numbering and restore usage, and tombstone persistence. No fluff, every sentence earns its place, and key details are front-loaded.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a simple read-only list tool with a single parameter and an output schema, the description covers all necessary context: what it returns, what it doesn't return, how to use the results with restore_app, and edge-case behavior (deleted apps). No missing critical information.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The schema only has a 'name' string with no description. The description's phrase 'an app's checkpoints' clearly implies 'name' is the app identifier, but it doesn't explicitly state that the parameter is the app name or define any format. Since schema coverage is 0%, the description provides just enough context but could be more explicit about the parameter's role.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific verb ('List') and resource ('an app's checkpoints') with an explicit output shape ({checkpoint, ts, ui_size}). It clearly distinguishes itself from get_app by saying 'metadata only, NEVER the source' and from restore_app by noting that checkpoint numbers are used by restore_app.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly tells when to use this tool: 'use get_app for the current source' for retrieving source, implying use app_history when you need checkpoint metadata. It also establishes a relationship with restore_app ('restore_app takes that number') and notes that history survives delete_app, which is useful for deleted apps.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

app_htmlApp HTML (internal)A
Read-only

Internal: returns raw app HTML plus its trust tier and capability grants for the universal loader widget. Not useful to call directly — use get_app to read source.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameYes

Output Schema

ParametersJSON Schema
NameRequiredDescription
cspNo
capsYes
htmlYes
nameYes
tierYes
authorYes
lockedYesa fixed system app (settings renders these read-only)
versionYes
collectionYesthe collection this app opens on
declarationNo

TDQS

A4.5/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true and openWorldHint=false, so safety is covered. The description adds useful context about what the tool returns (raw HTML, trust tier, capability grants) and marks it as internal, which helps the agent understand its intended scope.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Two concise sentences with no wasted words. The core behavior is front-loaded, and the routing guidance to get_app is placed second.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a simple one-parameter, read-only tool with an output schema, the description is complete. It covers purpose, internal status, return contents, and the appropriate alternative, leaving nothing critical missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The single required parameter 'name' has no schema description, and the description does not explicitly define it as the app name. However, the tool name and the phrase 'app HTML' make it inferable that 'name' identifies the target app, providing just enough semantic grounding.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific action and resource: it returns raw app HTML plus trust tier and capability grants for the universal loader widget. It also explicitly distinguishes itself from get_app, making the tool's purpose unambiguous.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly says this tool is 'Not useful to call directly' and tells the agent to 'use get_app to read source.' This provides clear when-not-to-use guidance and names the correct alternative.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

app_store_listList App Store appsA
Read-only

Browse the built-in App Store: ready-made, high-quality apps shipped with the engine that the user can install into their registry. Shows install state. Renders no UI — open_app {app: "app-store"} shows the browsable App Store app.

ParametersJSON Schema
NameRequiredDescriptionDefault

No parameters

Output Schema

ParametersJSON Schema
NameRequiredDescription
entriesYes

TDQS

A4.7/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description adds behavioral context beyond the annotations: it notes that the tool shows install state and renders no UI. This is consistent with readOnlyHint=true and provides useful additional insight into what the agent should expect from the tool's output and side effects.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is two sentences, with the primary purpose front-loaded in the first phrase. Every word contributes to meaning, and there is no redundancy or filler.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a zero-parameter read-only listing tool with an output schema and clear annotations, the description provides everything needed: what the tool lists, the install-state information, the no-UI behavior, and a pointer to the alternative for UI. No gaps remain.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The tool has zero parameters, so the description doesn't need to clarify parameter meanings. It adds value by describing the content of the list (ready-made, high-quality apps shipped with the engine) which helps the agent understand what the tool returns. Baseline for zero params is 4, and the description meets it.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool's function with a specific verb ('browse') and resource ('built-in App Store'), and distinguishes itself from sibling open_app by explicitly noting that it renders no UI. This makes its purpose unambiguous and differentiated.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly tells the agent when to use this tool: to browse the built-in App Store programmatically. It also provides an explicit alternative, open_app {app: "app-store"}, for when a UI is desired, making the usage boundaries clear.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

app_store_previewApp Store live-preview payload (internal)A
Read-only

Internal: returns an App Store entry's ui and manifest plus its mock-data fixtures, so the App Store app can render a LIVE sandboxed preview card (srcdoc + stub oma + mock snapshot). Read-only; nothing is installed. Not useful to call directly.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameYesApp Store entry name (see app_store_list)

Output Schema

ParametersJSON Schema
NameRequiredDescription
htmlYesthe entry's ui slot (field named for its format — the preview iframe srcdocs it)
nameYes
titleYes
categoryYes
fixturesYesembedded mock snapshot items, or null if the entry ships none
manifestYes
descriptionYes

TDQS

A4.3/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true. The description adds that 'nothing is installed' and describes the sandboxed nature with 'mock-data fixtures' and 'LIVE sandboxed preview card,' which goes beyond the annotation. No contradiction.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Two sentences, front-loaded with 'Internal,' and each sentence conveys a distinct piece of information: what it returns, why it exists, and that it's safe and not for direct use.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The tool has a single parameter, an output schema, and annotations. The description covers the purpose, internal nature, side-effect-free behavior, and sandboxed output. Nothing critical is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The only parameter 'name' is documented in the schema with reference to app_store_list, so coverage is 100%. The description itself doesn't add any parameter detail, so baseline 3 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description uses 'returns' as the verb and specifies the resource: an App Store entry's ui, manifest, and mock-data fixtures. The 'Internal' prefix and 'Not useful to call directly' clearly distinguish it from sibling tools like install_from_app_store or get_app. It's specific about the purpose: rendering a sandboxed preview card.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Explicitly marked 'Internal' and 'Not useful to call directly,' which tells agents not to invoke it directly. However, it does not name an alternative tool to use instead, so it earns a 4 rather than 5.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

call_functionCall an app functionA
Idempotent

Run a function an app declares (manifest.functions) — data in, data out, no UI needed. Args are checked against the declared params; failures return the declared schema so the retry needs no extra read. The reply carries the return value plus a receipt per write.

ParametersJSON Schema
NameRequiredDescriptionDefault
appYes
argsNo
actorNo
functionYes
command_idYesidempotency key — generate a fresh uuid per action

Output Schema

ParametersJSON Schema
NameRequiredDescription
okYes
eotNo
noteNo
reasonNo
resultNo
writesNo
availableNo
violationsNo

TDQS

A4.2/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already establish idempotency and non-read-only behavior. The description adds valuable details beyond that: argument validation against declared params, failure responses including the declared schema, and success replies containing the return value plus a per-write receipt. These behaviors are not present in annotations, enriching the agent's expectations without contradiction.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is two sentences, front-loaded with the core purpose, then adding behavioral details. Every clause adds information: purpose, no-UI nature, validation, error handling, and return content. There is no redundancy or filler.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool with 5 parameters, nested args, and an output schema, the description covers the essential operational aspects: what it does, how args are validated, how failures are reported, and what the success reply contains. It omits nuances like the actor enum's effect, but the output schema and overall clarity keep it reasonably complete.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

With only 20% schema description coverage, the description carries a heavier burden. It does clarify that 'args' are checked against the app's declared parameters, giving meaning to that field. However, it does not explain 'actor' or add any semantics beyond what the names imply for 'app' and 'function'. This is adequate but not fully compensating for the low coverage.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description starts with a specific verb-resource pairing: 'Run a function an app declares (manifest.functions)'. The added phrase 'data in, data out, no UI needed' immediately distinguishes this from UI-oriented siblings like open_app and app_html, making the tool's scope unmistakable.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description provides clear context that this is for headless function execution ('no UI needed') and even gives retry guidance after failures ('failures return the declared schema so the retry needs no extra read'). However, it does not explicitly name alternative tools or state when not to use it, stopping short of full exclusion guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

data_add_itemAdd itemA
Idempotent

Add an item to a collection. group is the app-defined lane/section (e.g. a kanban column); fields is a JSON object (e.g. {title, done, notes…}).

ParametersJSON Schema
NameRequiredDescriptionDefault
actorNo
groupNo
fieldsYes
positionNo
collectionYes
command_idYesidempotency key — generate a fresh uuid per action

Output Schema

ParametersJSON Schema
NameRequiredDescription
idNo
okYes
eotNo
seqNo
itemNo
noteNo
reasonNo
deletedNo
collectionNo
violationsNo
expected_versionNo
prev_collection_seqNo

TDQS

A3.7/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already indicate readOnlyHint=false, destructiveHint=false, and idempotentHint=true, so the safety profile is clear. The description adds context on 'group' and 'fields' but does not disclose additional behavioral traits such as side effects, ordering, or what happens if the collection doesn't exist. No contradiction with annotations is present.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is two sentences long, front-loaded with the core action, and uses no redundant words. It efficiently explains the tool's purpose and two key parameters without superfluous detail.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Despite having an output schema and annotations, the description leaves 'position' and 'actor' undefined, which are important for correct invocation. The core action is clear, but the tool has 6 parameters and nested objects, so a fully complete description should cover more parameter semantics. It meets the minimum viable threshold but has gaps.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is low (17%), so the description's clarification of 'group' as a lane/section and 'fields' as a JSON object with an example is valuable. However, 'position' and 'actor' remain unexplained, and 'collection' is only implied, not explicitly defined. The description partially compensates for the schema gaps but does not fully cover all parameters.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the action ('Add an item to a collection') with a specific verb and resource, distinguishing it from sibling tools like data_update_item, data_move_item, and data_delete_item. It also elaborates on the 'group' and 'fields' parameters, making the purpose unmistakable.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies usage for adding new items but does not explicitly state when to use this tool versus alternatives like data_update_item or data_move_item. There is no mention of exclusions or alternative scenarios, leaving the guidance implicit rather than explicit.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

data_batchMany writes, one transactionA
Idempotent

Apply up to 200 writes in ONE transaction — for seeding an app from what you already know, or filling a board in one go, instead of one call per row. Each command is exactly what you would send to data_add_item / data_update_item / data_move_item / data_delete_item, as {type, ...args}: type is add_item | update_item | move_item | delete_item. All or nothing: the first failure rolls back everything and names which command failed. The reply is one line per command ({id, seq}) — not the rows, which you already have.

ParametersJSON Schema
NameRequiredDescriptionDefault
actorNo
commandsYes[{type: "add_item", collection, fields, group?}, {type: "update_item", id, fields}, …] — same arguments as the single-write tools
command_idYesidempotency key — generate a fresh uuid per action

Output Schema

ParametersJSON Schema
NameRequiredDescription
okYes
eotNo
seqNothe batch's last ledger position — pass it to data_changes as `since`
noteNo
countNo
reasonNo
previewNo
resultsNo
expires_atNo
failed_indexNo
request_stateNo

TDQS

A4.9/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Discloses critical behavioral traits: all-or-nothing transaction with first-failure rollback and error naming, reply format ({id, seq}), and that rows are not returned. This goes well beyond the annotations, which only hint at idempotency and non-destructiveness, adding real operational context for the agent.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Four dense sentences, each earning its place: purpose, command format, transaction semantics, and response format. No filler or redundancy; the description is front-loaded with the most important constraint (ONE transaction, up to 200 writes).

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a complex batch tool, the description covers the essential operational aspects: usage examples, command schema (via reference to sibling tools), transaction behavior, failure reporting, and response format. The presence of an output schema reduces the need to detail return values, and annotations handle safety hints.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 67% (actor lacks description), but the description compensates by fully explaining the 'commands' array structure, linking each command to the corresponding single-write tool and enumerating the 'type' values. It also clarifies command_id as an idempotency key. The actor parameter remains undocumented in text but is self-evident via its enum.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

Specific verb+resource+scope: 'Apply up to 200 writes in ONE transaction' clearly states the batch-write purpose. The description explicitly differentiates from single-write tools with 'instead of one call per row' and lists the four supported write types, making the tool's role unmistakable.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Provides explicit use cases ('seeding an app' or 'filling a board in one go') and contrasts with alternatives ('instead of one call per row'). It also identifies the 200-write limit and implies when the tool is appropriate by mapping commands to the single-write tools.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

data_changesWhat changed since you last lookedA
Read-only

What happened in a collection after a ledger position YOU hold — including edits the USER made in the widget, which never pass through you. Any mark you already have works as since: a write ack's seq, data_list's version, or the last call's next_since. Returns the contiguous run of events right after it (oldest first, whole events: actor, item id, fields) plus next_since to continue; omit since to just learn the current position.

ParametersJSON Schema
NameRequiredDescriptionDefault
limitNomax events to return (default 50, max 500)
sinceNoyour held mark — events strictly after this seq; omit to just learn latest_seq
collectionYes

Output Schema

ParametersJSON Schema
NameRequiredDescription
eotNo
noteNo
sinceNo
totalNo
eventsYes
droppedNo
returnedNo
collectionYes
latest_seqYes
next_sinceYes

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Even with readOnlyHint=true, the description adds valuable behavioral context: it reveals that user widget edits are included in the change stream, events are returned oldest-first with full details (actor, item id, fields), and omitting 'since' only returns the current position. This goes well beyond the structured annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Three dense sentences carry the entire behavioral contract without repetition. The most important concept ('what changed since you last looked') is front-loaded, and every clause adds necessary detail about marks, return ordering, and event contents.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The description fully covers the tool's semantics: what events are returned, the meaning of 'since', how to continue paging via next_since, and the surprising inclusion of user widget edits. With an output schema present, there is no need to enumerate return fields, making this complete for the tool's complexity.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 67%, so the description's burden is moderate. It enriches the 'since' parameter by explaining acceptable mark types (write ack seq, data_list version, next_since) and the consequence of omitting it. It does not elaborate on 'collection', but the overall context is sufficient; the extra mark semantics push this above baseline.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description uses a specific verb ('returns') and clearly identifies the resource: a collection's event stream since a held ledger position. It distinguishes this from sibling tools by emphasizing that it includes edits made in the widget that never pass through the agent, which data_list and data_version do not cover.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description provides clear when-to-use guidance by explaining how any existing mark (write ack seq, data_list version, or next_since) serves as the 'since' parameter. It does not explicitly state when NOT to use this tool or name an alternative for full collection snapshots, though it references data_list's version as a source, which implies its role.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

data_collectionsList collectionsA
Read-only

List every data collection that exists (name, item count, last activity). Use when unsure where data lives, what boards the user has, or which collection to bind an app to. Renders no UI.

ParametersJSON Schema
NameRequiredDescriptionDefault

No parameters

Output Schema

ParametersJSON Schema
NameRequiredDescription
noteNo
collectionsYes

TDQS

A4.5/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true, covering the safety profile. The description adds useful behavioral context: it guarantees a full enumeration of all collections and explicitly states 'Renders no UI.' No contradiction with annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Three concise sentences, each delivering distinct value: what is listed, when to use the tool, and the rendering behavior. The core action is front-loaded with no filler.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a parameterless listing tool with an output schema and read-only annotation, this description covers scope, use cases, and behavioral nuance. Nothing essential for calling it correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The tool has zero parameters, so the schema conveys all there is to know. There is no parameter meaning for the description to clarify; baseline 4 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb ('List'), a clear resource ('every data collection that exists'), and the returned fields (name, item count, last activity). The phrase 'every data collection' distinguishes it from content-level tools like data_list, which operate on items within a collection.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Provides explicit when-to-use guidance: 'Use when unsure where data lives, what boards the user has, or which collection to bind an app to.' It does not explicitly list exclusions or name alternative tools, but the contexts are concrete enough to guide selection.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

data_delete_itemDelete itemA
DestructiveIdempotent

Delete an item permanently. May return reason:"confirmation_required" with a request_state — show the user what is named in note, then re-send the same call with request_state attached.

ParametersJSON Schema
NameRequiredDescriptionDefault
idYes
actorNo
command_idYesidempotency key — generate a fresh uuid per action
request_stateNo
expected_versionNo
require_confirmationNo

Output Schema

ParametersJSON Schema
NameRequiredDescription
idNo
okYes
eotNo
seqNo
itemNo
noteNo
reasonNo
deletedNo
previewNo
collectionNo
expires_atNo
violationsNo
request_stateNo
expected_versionNo
prev_collection_seqNo

TDQS

A3.9/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The annotations already indicate destructiveHint=true and readOnlyHint=false. The description adds valuable behavioral context beyond that: it discloses the confirmation_required behavior and guides the agent on how to handle it, including referencing the 'note' field. This is useful, even though 'note' is not defined in the schema.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is brief, two sentences, and front-loaded with the primary purpose. The second sentence is somewhat dense but still focused. No excessive words, though the wording could be clearer about the 'note' reference.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool has 6 parameters and an output schema, the description is moderately complete. It explains the confirmation flow, which is important for a destructive operation, but it omits details about other parameters and edge cases. The output schema exists, so return values are not required, but the description could be more thorough about the delete process.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters2/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is only 17%, so the description must compensate for the underdocumented parameters. It adds some meaning to request_state (required for confirmation flow) but does not explain actor, expected_version, require_confirmation, or the idempotency key usage beyond what the schema already says. The reference to 'note' is confusing because it is not a parameter.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the action and resource: "Delete an item permanently." It distinguishes from sibling tools like data_add_item, data_update_item, and data_move_item by specifying the permanent deletion operation.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description provides clear usage context when it explains the confirmation_required flow: show the note and resend with request_state. However, it does not explicitly discuss when to use it versus alternatives or exclusions, though that is somewhat implicit given the tool's name.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

data_listList collection dataA
Read-only

Read items in full — every field, plus the item id you need to update or delete it. No UI (use open_app for that). Returns a PAGE: up to limit (default 100) matching items, with total and — when more exist — next_cursor; returned/total make a short delivery self-evident. match filters: a bare value means equals; an object is operators {ne, lt, lte, gt, gte, contains, prefix, exists} (numeric filters compare numerically, strings lexicographically — ISO dates work). Paging is a live keyset walk; items moved mid-page can be skipped or repeated.

ParametersJSON Schema
NameRequiredDescriptionDefault
groupNoonly items in this group/lane
limitNopage size (1-500, default 100)
matchNofilter on top-level fields, e.g. {"done": false} or {"amount": {"gte": 100}}
cursorNoopaque cursor from the previous page's next_cursor
collectionYes

Output Schema

ParametersJSON Schema
NameRequiredDescription
okNo
eotNo
hostNo
noteNo
groupNo
itemsYes
totalNohow many items exist (the collection/group, pre-filter) — compare it with the rows you actually received
versionYes
returnedNo
collectionYes
next_cursorNopass back as `cursor` for the next page; null = no more
files_versionNo
settings_versionNo

TDQS

A5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the readOnlyHint annotation, the description discloses key behavioral details: paging follows a 'live keyset walk,' items can be skipped or repeated, pages contain limit/total/next_cursor, and match has operator semantics. This adds substantial operational context that annotations alone do not provide.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but every sentence contributes: purpose, UI exclusion, page shape, filter semantics, and paging caveat. It front-loads the core behavior and groups related concepts cleanly without redundant restatement of schema fields.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a 5-parameter tool with an output schema, the description covers selection scope, filtering operators, paging behavior, and edge cases. The output schema handles return-value structure, so nothing essential is missing for an agent to invoke this tool correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters5/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is already high at 80%, but the description adds crucial meaning: it explains the match parameter's bare-value-equals behavior, lists available operators, and specifies numeric versus lexicographic comparison. It also clarifies paging semantics tied to limit and cursor beyond the schema descriptions.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Read items in full,' and explicitly states the output includes 'every field, plus the item id you need to update or delete it.' It also distinguishes itself from a UI tool ('No UI (use open_app for that)'), making its scope clear relative to siblings.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It gives explicit routing guidance by stating 'No UI (use open_app for that)' and frames the tool as the way to obtain item IDs needed for update or delete operations. This tells an agent when to use data_list versus relevant alternatives like open_app or mutation tools.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

data_move_itemMove itemA
Idempotent

Move an item to another group and/or position (e.g. kanban column).

ParametersJSON Schema
NameRequiredDescriptionDefault
idYes
actorNo
groupNo
positionNo
command_idYesidempotency key — generate a fresh uuid per action
expected_versionNo

Output Schema

ParametersJSON Schema
NameRequiredDescription
idNo
okYes
eotNo
seqNo
itemNo
noteNo
reasonNo
deletedNo
collectionNo
violationsNo
expected_versionNo
prev_collection_seqNo

TDQS

A3.7/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=false, destructiveHint=false, and idempotentHint=true, covering the safety profile. The description adds the operation semantics but does not disclose additional behaviors such as optimistic concurrency via expected_version or the role of the idempotency key.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is a single, well-structured sentence that is front-loaded and concise. Every word adds value, with an example to clarify the use case.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The description is minimally viable given the annotations and output schema, but it lacks guidance on when to use this versus data_update_item and does not address the expected_version or actor parameters. It is adequate but not comprehensive for a mutation tool.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The description clarifies the purpose of 'group' and 'position' by tying them to the move operation, but schema description coverage is only 17%. It does not explain parameters like expected_version or actor, leaving a gap for a 6-parameter tool.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the action ('Move an item') and the target scope ('to another group and/or position'), with a concrete example ('e.g. kanban column'). This distinguishes it from sibling tools like data_update_item or data_delete_item.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies when to use it (when you need to change an item's group or position) but does not explicitly mention alternatives or exclusions. It falls short of naming other data_* tools or stating when not to use it.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

data_update_itemUpdate item fieldsA
Idempotent

Shallow-merge fields into an item (set a key to null to remove it). Uses optimistic concurrency.

ParametersJSON Schema
NameRequiredDescriptionDefault
idYes
actorNo
fieldsYes
command_idYesidempotency key — generate a fresh uuid per action
expected_versionNothe item version you last saw

Output Schema

ParametersJSON Schema
NameRequiredDescription
idNo
okYes
eotNo
seqNo
itemNo
noteNo
reasonNo
deletedNo
collectionNo
violationsNo
expected_versionNo
prev_collection_seqNo

TDQS

A4.2/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the annotations (non-read-only, non-destructive, idempotent), the description discloses shallow-merge semantics, null-based field removal, and optimistic concurrency. It does not cover conflict error handling or permission requirements, but the optimistic concurrency mention is a valuable behavioral hint.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is two short sentences with no filler. It front-loads the verb and object, uses a parenthetical for the key removal detail, and ends with a concise concurrency note.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool with an output schema and annotations, the description covers the core behavioral contract well. The only minor gap is the lack of explicit conflict-handling guidance, but the optimistic concurrency mention plus the schema's expected_version description suffice.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is only 40%, and the description compensates for the 'fields' parameter by explaining shallow merge and null removal. It also hints at expected_version via optimistic concurrency, but leaves 'actor', 'id', and 'command_id' semantics to the schema or inference.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific action ('Shallow-merge fields into an item') with a clear resource (an item) and defines the semantics of key removal via null. This clearly distinguishes it from sibling tools like data_add_item, data_delete_item, and data_move_item.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description clearly implies the tool is for updating existing items via shallow merge, and the null-removal note adds important usage detail. It doesn't explicitly state exclusions or alternatives, but the operation is distinct enough within the data_* sibling group.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

data_versionData change probeA
Read-only

The cheapest possible change check: returns the global change counter (seq) plus settings/files sub-counters. If seq hasn't moved since you last looked, NOTHING changed anywhere — skip re-reading. Widgets use this for adaptive polling; you can too before re-listing a collection.

ParametersJSON Schema
NameRequiredDescriptionDefault

No parameters

Output Schema

ParametersJSON Schema
NameRequiredDescription
seqYes
files_versionYes
schema_versionYes
settings_versionYes

TDQS

A4.7/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true and openWorldHint=false, so the safety profile is covered. The description adds valuable behavioral context: the meaning of seq as a global change indicator, the existence of sub-counters, and the cost-effectiveness ('cheapest possible'). This goes beyond the structured annotations, though it doesn't discuss edge cases or rate limits.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is three sentences, each earning its place: first states what it returns, second explains the decision rule, third provides context. No fluff or repetition.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a simple no-parameter tool with an output schema, the description fully covers purpose, usage, and behavioral implications. It explains when to use (before re-listing) and what the return value indicates, making it complete for an agent to decide and invoke.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The tool has zero parameters, so the baseline is 4. The schema coverage is trivially 100%, and the description doesn't need to explain parameters. It adds no additional parameter semantics but none are needed.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool returns the global change counter (seq) plus sub-counters, with a specific verb ('returns') and resource ('change counter'). It also distinguishes itself from siblings like data_changes by positioning as 'the cheapest possible change check' and explaining its use for skip re-reading.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Provides explicit when-to-use guidance: 'If seq hasn't moved since you last looked, NOTHING changed anywhere — skip re-reading' and 'Widgets use this for adaptive polling; you can too before re-listing a collection.' This tells the agent exactly the context for using this tool over alternatives.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

delete_appDelete appA
DestructiveIdempotent

Delete an app from the registry. Default data:"keep" is a tombstone: its data, files and history are KEPT and restore_app can bring the app back. data:"cascade" ALSO permanently deletes the data provably only this app used (plus its settings) — it always returns a disposition plan first: read the plan to the user (what will be deleted AND what will be kept and why), then re-send the same call with request_state. Cascade is NOT undoable. Shared or unprovable collections are always kept.

ParametersJSON Schema
NameRequiredDescriptionDefault
dataNo"keep" (default): tombstone, data survives. "cascade": delete the app AND the data only it used — two-step confirmed, permanent
nameYes
actorNo
command_idYesidempotency key — generate a fresh uuid per action
request_stateNothe state from a prior confirmation_required answer — re-send the identical call with it attached

TDQS

A4.8/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description adds substantial behavioral context beyond the annotations: tombstone semantics (data/files/history kept), cascade's two-step confirmation with disposition plan, and the permanent, non-undoable nature of cascade. It also clarifies that shared or unprovable collections are always kept, which is critical for understanding the tool's impact. No contradiction with annotations; destructiveHint and idempotentHint are consistent.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but efficient; every sentence adds critical information about behavior or usage. It is front-loaded with the primary action and then elaborates on modes and confirmation. Slightly lengthy due to the complexity of the cascade flow, but still concise given the tool's nuance.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a destructive tool with no output schema, the description is remarkably complete. It covers the two deletion modes, the irreversible-cascade chain, the disposition plan requirement, and the preservation rules for shared/unprovable collections. This provides enough context for an agent to execute correctly and explain the outcome to a user.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The description significantly enhances understanding of the 'data' parameter by explaining tombstone vs cascade and the request_state flow. However, it does not cover the semantics of 'name', 'actor', or 'command_id' beyond the schema (which itself omits descriptions for name and actor). With schema coverage at 60%, the description partially compensates but leaves some param meanings implicit.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states 'Delete an app from the registry' — a specific verb and resource. It further distinguishes two deletion modes ('keep' tombstone vs 'cascade' permanent) and explicitly references restore_app as the undo path, setting it apart from sibling tools like restore_app and file_delete.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Provides explicit guidance on when to use each mode: use 'keep' for a reversible tombstone and 'cascade' for permanent deletion. It instructs the agent to read the disposition plan to the user and re-send with request_state, effectively outlining the confirmation workflow. Also warns that cascade is not undoable and that shared/unprovable collections are always kept, helping the agent decide appropriately.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

edit_appEdit app sourceA
Idempotent

Surgical edits to an app WITHOUT round-tripping the whole source. Two edit forms, mixable: RANGE {offset, length, expect_hash, new_string} replaces a span you read with get_app (cheapest — echo the window's offset/returned/hash, no anchor text travels); STRING {old_string, new_string} replaces an exact-once match (or set replace_all). Range offsets always address the expected_version document and must not overlap; string edits apply after ranges, in order. All edits apply together, or nothing applies. The #oma-manifest block is re-read on save.

ParametersJSON Schema
NameRequiredDescriptionDefault
appYesapp name (this tool says `app`; save_app and get_app say `name`)
actorNo
editsYeseach item is RANGE (offset+length+expect_hash) or STRING (old_string)
command_idYesidempotency key — generate a fresh uuid per action
expected_versionYesREQUIRED — the version the edits were authored against (from get_app)

Output Schema

ParametersJSON Schema
NameRequiredDescription
okYes
eotNo
nameNo
noteNo
sizeNo
reasonNo
appliedNo
createdNo
versionNo
prev_sizeNo
manifest_actionNo
expected_versionNo

TDQS

A4.9/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond annotations, the description reveals important behaviors: edits apply atomically, range offsets address the expected_version document, string edits apply after ranges, and the #oma-manifest block is re-read on save. This adds meaningful context not visible in the annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but every sentence earns its place: purpose, form definitions, ordering, overlap constraint, atomicity, and manifest behavior. It is front-loaded with the core distinction and uses compact, meaningful phrasing.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity and the rich schema/output schema, the description covers the essential operational details: edit forms, constraints, ordering, atomicity, and expected_version source. Nothing critical for an agent to call it correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The schema already covers most parameters (80%), so the baseline is 3, but the description adds value by explaining the RANGE and STRING forms, the exact-once matching rule for old_string, replace_all, and the relationship between offset/length/expect_hash and get_app output.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific verb and resource: 'surgical edits to an app' without round-tripping the whole source. It clearly distinguishes itself from full-source alternatives like save_app and names the two edit forms, RANGE and STRING, with concrete semantics.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It explicitly says when to use this tool (surgical edits, not full round-trip), how to choose between RANGE and STRING forms, and gives ordering constraints (string edits apply after ranges). It also references get_app for the expected_version and range hashes, providing clear operational guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

file_deleteDelete an app fileA
DestructiveIdempotent

Permanently delete one file an app has stored.

ParametersJSON Schema
NameRequiredDescriptionDefault
appYes
pathYes
actorNo
command_idYesidempotency key (uuid)
request_stateNo
expected_versionNo

Output Schema

ParametersJSON Schema
NameRequiredDescription
okNo
appYes
noteNo
pathYes
reasonNo
deletedNo
previewNo
expires_atNo
files_versionNo
request_stateNo

TDQS

A3.8/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare destructiveHint=true and readOnlyHint=false. Description adds 'permanently' which indicates irreversibility, and specifies scope to files an app has stored. However, no details on error behavior or version considerations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

One sentence, front-loaded, no waste. Directly communicates action and scope.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Tool has 6 parameters and output schema, but description is extremely minimal. It doesn't address idempotency implications or concurrency controls (expected_version). However, given annotations and output schema, it's moderately complete for a simple delete.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters2/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is only 17% (command_id), and description provides no parameter explanations. Parameter names are self-evident, but description does not clarify semantics for expected_version, actor, or request_state.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

Description uses specific verb 'Permanently delete' and resource 'one file an app has stored,' clearly distinguishing from delete_app and file_write tools. Scope is precise.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

No explicit guidance on when to use vs alternatives like file_write or delete_app. Context implies deletion of app-stored files, but no direct exclusions.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

file_listList app filesA
Read-only

List the files an app (app) has stored — a PAGE of {path, size, mime, version} plus usage totals; limit/cursor page through, prefix narrows. These are opaque user files (attachments, exports) the app keeps — separate from its structured data collection. Renders no UI.

ParametersJSON Schema
NameRequiredDescriptionDefault
appYesthe app whose files to list
limitNopage size (default 200)
cursorNoopaque cursor from the previous page's next_cursor
prefixNoonly paths starting with this prefix

Output Schema

ParametersJSON Schema
NameRequiredDescription
appYes
eotNo
noteNo
filesYes
totalNo
usageYes
returnedNo
next_cursorNo
files_versionYes

TDQS

A4.2/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description goes beyond readOnlyHint=true by disclosing pagination mechanics ('limit/cursor page through'), prefix narrowing, and that it returns a page plus usage totals rather than a flat list. 'Renders no UI' is a genuinely useful behavioral exclusion. Annotations already cover the read-only safety profile, so the description adds meaningful behavior context without contradicting them.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Three terse, information-dense sentences with the core purpose and return shape front-loaded, followed by only the details that disambiguate it from siblings. No filler; every clause earns its place.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a read-only list tool with a 100%-documented schema, a true output schema, and safety annotations, the description is nearly complete: it covers return fields, paging, filtering, and file-type semantics. Minor gaps remain — behavior for a nonexistent app, permission requirements, and explicit differentiation from file_read — so it falls just short of a 5.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so all four parameters are already documented individually. The description adds only the relational framing that limit/cursor form a paging mechanism and prefix narrows, which is mildly useful but largely redundant with the schema's own notes (e.g., 'opaque cursor from the previous page's next_cursor'). Baseline 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb ('List') and resource (the files an app has stored), and names the return shape ({path, size, mime, version} plus usage totals), distinguishing it at a glance from data_list. It also clarifies what the files are (opaque user files like attachments/exports) and what the tool is not ('Renders no UI').

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Provides clear context: 'These are opaque user files... separate from its structured data collection' implicitly routes structured-data queries to the data_* siblings. It stops short of explicitly naming alternatives or stating when not to use it, so it is contextual rather than fully prescriptive.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

file_readRead an app fileA
Read-only

Read one file an app has stored, as a WINDOW of its bytes: offset/length select it, data_base64 carries exactly that window, next_offset continues (same window grammar as get_app, and for the same reason). Reassemble by concatenating decoded windows; sha256 is the WHOLE file's hash, so reassembly is checkable.

ParametersJSON Schema
NameRequiredDescriptionDefault
appYes
pathYesthe file's logical name
lengthNomax bytes for this window (default fits the result budget)
offsetNobyte offset to read from (default 0)

Output Schema

ParametersJSON Schema
NameRequiredDescription
appYes
eotNo
mimeYes
pathYes
sizeYes
totalNo
offsetNo
sha256Yes
versionYes
returnedNo
data_base64No
next_offsetNo

TDQS

A4.2/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the readOnlyHint annotation, the description discloses the full windowing contract: offset/length select the window, data_base64 carries exactly that window, next_offset continues, and sha256 hashes the whole file so reassembly is verifiable. This is substantial operational context that annotations and schema alone do not provide.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact and front-loaded with the core action. Every sentence contributes useful information: window selection, continuation semantics, and reassembly/integrity checking, with no filler or repetition of schema details.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a windowed file reader, the description covers selection, continuation, reassembly, and integrity checking. With an output schema present, this is sufficient for an agent to call the tool correctly and handle multi-window reads without additional inference.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The schema already documents path, length, and offset, and the description reinforces their interaction: offset and length select the byte window, and next_offset continues reading. It adds useful meaning about reassembly and whole-file sha256 verification, though the app parameter remains undocumented.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a clear, specific action: 'Read one file an app has stored' and identifies the resource as an app-stored file with windowed byte access. It is unambiguous about what the tool does, though it does not explicitly contrast itself with sibling tools like get_app or file_list.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The intended use is implied: use this when you need to read the contents of one of an app's stored files, especially when windowed reads are needed. It references the same window grammar as get_app, but it does not explicitly state when to prefer file_read over alternatives or when not to use it.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

file_writeStore an app fileA
DestructiveIdempotent

Store a file for an app (create or overwrite by path). data_base64 is the file bytes, base64-encoded — pass any file the user gave you or that you generated. Overwriting an existing path bumps its version. Single-call writes are limited to a few MiB. Files persist and are the app's own, reusable across chats.

ParametersJSON Schema
NameRequiredDescriptionDefault
appYesthe app this file belongs to
mimeNocontent type, e.g. 'image/png' (default application/octet-stream)
pathYeslogical file name, e.g. 'receipt.pdf' or 'exports/2026-q1.csv'
command_idYesidempotency key — a fresh uuid per write
data_base64Yesfile bytes, base64-encoded
expected_versionNothe version you last saw, for optimistic concurrency (optional)

Output Schema

ParametersJSON Schema
NameRequiredDescription
appYes
mimeYes
pathYes
sizeYes
sha256Yes
versionYes
files_versionYes

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the annotations (destructive, idempotent), the description adds valuable behavioral details: overwriting bumps version, writes are limited to a few MiB, files persist, and are app-owned and reusable across chats. This enriches the agent's understanding of side effects and constraints without contradicting any annotation.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Four sentences, front-loaded with the core purpose, and every sentence contributes meaningful information (purpose, data_base64 handling, version bump, size limit, persistence). No redundant wording or filler.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the output schema exists, the description fully covers the essential context: file persistence, overwrite behavior, versioning, size constraints, and cross-chat reusability. It is complete enough for an agent to use the tool correctly without further clarification.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, but the description elevates the meaning of data_base64 with explicit guidance ('pass any file the user gave you or that you generated') and clarifies overwrite/version semantics that tie to expected_version. Other parameters are adequately self-describing in the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool's function: 'Store a file for an app (create or overwrite by path).' The verb 'store' plus the resource 'app file' and the create/overwrite behavior precisely distinguish it from sibling tools like file_write_begin and file_write_chunk, which handle multi-part writes.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description provides clear context: it accepts any file the user gave or the agent generated, and it notes that single-call writes are limited to a few MiB, implying larger files should use the chunked write tools. However, it does not explicitly name the alternative tools, so it stops short of a fully explicit when-not-to-use directive.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

file_write_beginBegin a chunked file writeA

Start a chunked upload for a file too big for file_write's single call. Returns an upload_id; send the bytes in order with file_write_chunk (each chunk up to ~5 MiB of raw bytes), then file_write_commit names the file. Uploads expire after 30 idle minutes; per-file ceiling 250 MiB.

ParametersJSON Schema
NameRequiredDescriptionDefault
appYesthe app this file will belong to

Output Schema

ParametersJSON Schema
NameRequiredDescription
upload_idYes
file_limit_bytesYes
chunk_limit_bytesYes

TDQS

A4.5/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=false, so write behavior is known. The description adds valuable beyond annotations: uploads expire after 30 idle minutes, per-file ceiling is 250 MiB, and an upload_id is returned. This contextualizes the operation's lifecycle without contradicting annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact yet information-dense. Each sentence serves a purpose: stating the trigger condition, outlining the workflow steps, and noting limits. No filler or redundant phrasing.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool is part of a multi-stage process, the description explains the entire flow (begin → chunk → commit) and critical constraints. It also notes an upload_id is returned, and since an output schema exists, return-value details are not required. Context is complete for an agent to select and invoke correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The only parameter 'app' is fully described in the schema as 'the app this file will belong to' (100% coverage). Since the schema carries the full parameter meaning, the description need not add more. It does not provide extra parameter details, matching the baseline for high coverage.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool's purpose: 'Start a chunked upload for a file too big for file_write's single call.' It uses a specific verb and resource, and distinguishes from siblings by explicitly referencing the chunked upload workflow and naming file_write, file_write_chunk, and file_write_commit.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Explicit when-to-use guidance is provided: 'for a file too big for file_write's single call.' It also maps the full sequence of operations: returns upload_id, use file_write_chunk to send bytes, then file_write_commit to name the file. Additionally, it includes expiration and size constraints that affect when to use.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

file_write_chunkAppend a chunk to an uploadA

Append the next chunk of bytes (base64) to an upload started with file_write_begin. Send chunks strictly in order, one at a time. Pass seq (0-based chunk index) so a resend after a lost response is acknowledged instead of double-appended.

ParametersJSON Schema
NameRequiredDescriptionDefault
seqNo0-based index of this chunk — a resend of an already-staged index is a safe no-op
upload_idYes
data_base64Yesthis chunk's bytes, base64-encoded

Output Schema

ParametersJSON Schema
NameRequiredDescription
bytesYestotal bytes staged so far
chunksNo
duplicateNo
upload_idYes

TDQS

A4.4/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already provide safety flags (readOnlyHint false, etc.). The description adds valuable behavioral context: chunks must be strictly ordered, and resending with the same seq is a safe no-op. This goes beyond annotations without contradicting them.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Two focused sentences: the first states purpose, the second explains ordering and retry semantics. No redundancy, front-loaded, every word earns its place.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool in a multi-step upload flow, the description covers essential lifecycle context (started with file_write_begin), ordering, and retry safety. Output schema exists, so return values are documented elsewhere. Missing explicit error cases but not necessary for core usage.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema covers two of three parameters with descriptions (seq and data_base64). The description reinforces seq's purpose (0-based index for safe resend), adding meaning beyond the schema's description. upload_id lacks description, but the coverage is sufficient.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool appends the next chunk of base64 bytes to an upload started with file_write_begin. It names a specific verb and resource, and the mention of file_write_begin distinguishes it from sibling tools like file_write_commit and file_write.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It implicitly defines when to use: after file_write_begin, before commit, and explicitly requires sending chunks in order, one at a time. It also explains safe resend behavior with seq, giving clear usage context. However, it does not explicitly name alternatives or exclusion criteria.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

file_write_commitCommit a chunked file writeA
DestructiveIdempotent

Finalize an upload as an app file (create or overwrite by path) — the chunked equivalent of file_write. The upload is consumed either way; on failure, restart from file_write_begin.

ParametersJSON Schema
NameRequiredDescriptionDefault
mimeNo
pathYeslogical file name, e.g. 'video.mp4' or 'exports/backup.zip'
upload_idYes
command_idNoidempotency key (uuid); auto-generated if omitted. A retried commit with the same id returns the original receipt instead of demanding a re-upload
expected_versionNo

Output Schema

ParametersJSON Schema
NameRequiredDescription
appYes
mimeYes
pathYes
sizeYes
sha256Yes
versionYes
files_versionYes

TDQS

A4.2/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already indicate destructive and idempotent behavior, but the description adds valuable context: the upload is consumed regardless of success or failure, and retries from file_write_begin are the recovery path. This goes beyond the annotation flags and helps the agent understand the consequences.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is two sentences with no redundancy. It front-loads the purpose and includes a critical behavioral note about upload consumption and restart, making every word count.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The tool is moderately complex due to the chunked upload workflow, but the description covers the finalization action, the equivalence to file_write, and failure recovery. Output schema exists, so return details are not needed. The main gap is parameter documentation, but overall the picture is reasonably complete.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is only 40%, and the description does not compensate by explaining parameters like mime or expected_version. It implicitly clarifies the role of path (target file name) and upload_id (the upload), but does not add enough detail to fully overcome the schema gaps.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool finalizes a chunked upload into an app file, using specific verbs like 'finalize' and 'create or overwrite'. It distinguishes itself from file_write by calling itself the chunked equivalent, which precisely identifies its role among sibling tools.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explains this is the chunked counterpart to file_write, implying it is used after chunked upload steps. It also provides a clear 'on failure, restart from file_write_begin' guideline, giving a recovery path. While it does not explicitly list when-not-to-use or alternative tools, the context is strongly implied.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

get_appGet app sourceA
Read-only

Read an app's ui source as a WINDOW — offset/length select it, next_offset continues, total is the full length. Windows exist because some hosts silently drop the MIDDLE of an oversized result: a big app read whole can arrive mutilated with no sign, and an edit saved from it destroys the source. Carries version — the expected_version for edit_app / save_app — and hash, the expect_hash for a range edit of exactly this window. node jumps the window to the element marked data-oma-node="". slot:"manifest" returns the declaration object instead (no window mechanics).

ParametersJSON Schema
NameRequiredDescriptionDefault
nameYes
nodeNoread the element marked data-oma-node="<node>" — the window (and its hash) covers exactly that element (ui slot only)
slotNodefault ui; manifest returns {manifest: object|null} whole
lengthNomax characters for this window (default fits the result budget; ui slot only)
offsetNocharacter offset to read from (default 0; ui slot only)

Output Schema

ParametersJSON Schema
NameRequiredDescription
eotNo
hashNo
nameYes
textNo
totalNo
offsetNo
versionYes
manifestNo
returnedNo
next_offsetNo

TDQS

A4.6/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the readOnlyHint annotation, the description discloses mutilation risk, the destructive consequence of editing from a mutilated read, next_offset/total continuation semantics, node-based jumps, and version/hash expectations. This is rich, non-obvious behavior that annotations alone would not convey.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but each sentence earns its place: window mechanics, safety rationale, version/hash, node behavior, and manifest behavior. There is no redundancy or filler.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a complex windowed-read protocol, the description covers the window mechanism, continuation, safety rationale, edit-handshake values, node targeting, and the manifest alternative. Nothing essential for correct invocation appears to be missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters5/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is high, but the description adds real meaning beyond the schema: offset/length define a selectable window, next_offset continues it, total is full length, node targets an element, slot:manifest bypasses window mechanics, and version/hash feed later edit operations. This goes far beyond the parameter descriptions.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific verb and resource ('Read an app's ui source') and adds clear windowing mechanics plus a manifest slot alternative. It is much more specific than the title, but it does not explicitly name or contrast sibling tools, so it stops just short of full differentiation.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It gives strong contextual guidance: windowed reads exist because oversized results may be silently mutilated, and the returned version/hash are meant for edit_app/save_app. It does not explicitly list when to use an alternative tool, but it conveys the right decision context.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

get_app_guideApp authoring guideA
Read-only

READ THIS FIRST before creating or editing an app. Returns the window.oma API contract, available CSS design tokens, the data model, and a minimal working app template.

ParametersJSON Schema
NameRequiredDescriptionDefault
topicNowhich chapter (default basics: the contract + template). Each chapter stands alone

TDQS

A4.4/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true, so the safe read nature is known. The description adds behavioral context by enumerating what the guide contains (contract, tokens, data model, template), making the tool's output predictable. It does not introduce contradictions and offers meaningful detail beyond the structured annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is two punchy sentences: the first delivers an imperative usage directive, the second lists the concrete contents. No filler or redundancy; every word earns its place and the most important instruction is front-loaded.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a simple guide tool with one optional enum parameter and no output schema, the description covers the core return value well (contract, tokens, model, template). It does not list the individual chapters (functions, embed, style), but those are enumerated in the schema, so completeness is adequate. Slightly more detail about how the topic parameter alters the output would push it to 5.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%: the 'topic' parameter is fully documented with an enum and a clear description ('which chapter... Each chapter stands alone'). The tool description does not need to repeat this. It neither adds nor detracts, so the baseline of 3 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description uses a specific verb ('Returns') and names the exact resources delivered: the window.oma API contract, CSS design tokens, data model, and a minimal working app template. It also includes an explicit 'READ THIS FIRST' instruction, clearly distinguishing it as an orientation/guide tool from siblings like get_app or edit_app.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The opening 'READ THIS FIRST before creating or editing an app' is an explicit when-to-use directive. It signals the tool is a prerequisite step before mutation tools like save_app or edit_app. The description does not list alternatives, but the strong directive makes usage context unambiguous.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

install_from_app_storeInstall an App Store appA
Idempotent

Install (or update) a ready-made app from the built-in App Store into the user's registry. Once installed it behaves like any app of the user's own; its UI updates come from the App Store (newer store version), not from edits. Use app_store_list to see what's available. Installing is HALF the job: before handing it over, seed the collection with the user's real rows (data_batch, from what you already know of them) — an installed app opened empty and generic is half-delivered.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameYesApp Store entry name (see app_store_list)
command_idNoidempotency key (uuid); auto-generated if omitted

Output Schema

ParametersJSON Schema
NameRequiredDescription
nameYes
tierYes
updatedNo
versionYes

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the annotations (idempotent, non-destructive), the description reveals that installed apps rely on the store for UI updates and that seeding data via data_batch is critical to avoid a half-delivered app. This is important behavioral context not present in annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is concise and front-loaded with the core purpose, followed by usage and a high-value workflow warning. Every sentence earns its place with no fluff.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's simplicity (2 parameters, output schema present) and good annotations, the description covers purpose, usage, and behavioral expectations comprehensively. No significant gaps remain.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema already fully documents both parameters (name and command_id), so the description adds no new parameter-level meaning. The mention of app_store_list for the name parameter is already captured in the schema's description.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool installs or updates a ready-made app from the built-in App Store into the user's registry. It uses specific verbs and resources, and distinguishes from siblings by mentioning app_store_list and contrasting with edits.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It instructs to use app_store_list to see what is available, and notes that UI updates come from the App Store rather than edits, implying this tool is for installing/updating store apps instead of editing them. This provides clear when-to-use and when-not-to-use guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

list_appsList appsA
Read-only

List UI apps in the registry (reusable across all chats). If the UI the user wants already exists, prefer opening it over creating a new one. Lists the user's openable apps by default — pass name to look one up, or widen with kind/visibility.

ParametersJSON Schema
NameRequiredDescriptionDefault
kindNodefault app: what a person opens and reuses
nameNoexact app name — the fastest way to answer "open my X"
visibilityNodefault featured+listed; archived/unlisted are retired or long-tail

TDQS

A4.5/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true, so the read-only nature is known. The description adds behavioral context by noting the registry is reusable across chats, lists the user's openable apps by default, and allows widening via kind/visibility.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Three sentences, front-loaded with the core purpose, each adding meaningful information: registry scope, the reuse-over-create guideline, and parameter usage. No wasted words or redundancy.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a read-only list tool with three optional params and no output schema, the description covers the essential context: what is listed, default filtering, lookup behavior, and how to broaden the search. It is self-sufficient and well-rounded.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema covers 100% of parameters with descriptions, so baseline is 3. The description adds value by mapping parameters to use cases: 'pass name to look one up' and 'widen with kind/visibility', which clarifies intent beyond enum definitions.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool lists UI apps in the registry, with a specific resource ('UI apps') and scope ('reusable across all chats'). It distinguishes itself from creating or opening apps by framing the registry as a lookup surface.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Provides explicit guidance: 'prefer opening it over creating a new one' and explains how to narrow results with name or widen with kind/visibility. It does not name sibling tools explicitly but gives enough context for choosing this over a create/open action.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

open_appOpen any appA
Read-only

Open ANY app from the registry by name as an interactive widget — use when the user wants to SEE or OPERATE the data (to merely read facts, use data_list — no UI). Works IMMEDIATELY for apps saved moments ago in this same chat (the dedicated open_ tools may take a while to appear). Prefer reusing an app on a different collection over creating near-duplicate apps.

ParametersJSON Schema
NameRequiredDescriptionDefault
appYesapp name in the registry (see list_apps)
collectionNodata collection to bind (default: the one the app declares, else its own name)

Output Schema

ParametersJSON Schema
NameRequiredDescription
okNo
appYes
eotNo
hostNo
noteNo
itemsYes
totalNo
versionYes
returnedNo
collectionYes
files_versionNo
settings_versionNo

TDQS

A4.5/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true and openWorldHint=false. The description adds useful behavioral context by framing the result as an 'interactive widget,' noting immediate availability for recently saved apps, and comparing against dedicated open_<name> tools. It does not contradict the annotations, though it could elaborate on what an interactive widget entails.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact—three sentences, each earning its place: purpose, usage/alternative, and preference. It front-loads the core action and keeps supporting information tightly relevant.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's simplicity (2 params, output schema available, read-only annotations), the description covers the essential context: purpose, usage scenario, timing, and a best practice for reuse. The output schema handles return-value details, so no further description is needed.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100% for both parameters, so the schema carries the parameter details. The description reinforces that the app parameter names a registry app and hints at collection binding via the reuse guidance, but does not add substantial new meaning beyond the structured schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb-resource pairing: 'Open ANY app from the registry by name as an interactive widget.' It immediately distinguishes from data_list ('no UI') and dedicated open_<name> tools, making the tool's role unambiguous.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Explicitly states when to use the tool ('when the user wants to SEE or OPERATE the data') and identifies the alternative for reading facts (data_list). It also gives timing guidance (works immediately for recently saved apps vs dedicated tools that may take a while) and a reuse preference for collections.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

promote_appPromote visual to appA
Idempotent

Upgrade a kind:"visual" app to a full app in ONE atomic step: the engine flips kind in the stored manifest, keeping every other declared key, and saves a new version (OCC-guarded, history kept). Already an app is a no-op; downgrades are refused — demoting is an author edit (save_app with the manifest), not a lifecycle verb.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameYesan existing app with kind "visual" (list_apps {kind:"visual"} shows them)
command_idNoidempotency key (uuid); auto-generated if omitted

Output Schema

ParametersJSON Schema
NameRequiredDescription
okYes
eotNo
wasNo
kindNo
nameNo
noteNo
reasonNo
versionNo

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description goes well beyond annotations by detailing the atomic nature, preservation of other keys, OCC guard, new version creation with history, no-op for existing apps, and refusal to downgrade. It also clarifies idempotency via command_id, aligning with the idempotentHint annotation. No contradiction with annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact yet packed with essential information: action, effects, constraints, and alternatives. Each clause serves a purpose (atomicity, manifest behavior, versioning, no-op, downgrade refusal). No redundant or filler content.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's moderate complexity, the description covers the core behavior, edge cases (no-op for already apps, downgrade refusal), and security/correctness aspects (OCC-guarded, history kept). An output schema exists, so return values are not required in the description. The description is sufficient for an agent to correctly select and invoke the tool.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100% for both parameters (name, command_id), each with meaningful descriptions. The tool description adds no further parameter-specific semantics, but the schema already handles this, earning the baseline 3.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool's purpose: upgrading a 'visual' app to a full app by flipping the kind in the manifest. It uses specific verbs ('Upgrade', 'promote'), identifies the resource ('kind:"visual" app'), and distinguishes from sibling tools like save_app by explicitly noting demotion is handled elsewhere.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Explicitly provides when-to-use and when-not-to-use guidance: 'Already an app is a no-op' indicates the tool is only for visual apps, and 'downgrades are refused — demoting is an author edit (save_app with the manifest)' names the alternative tool for demotion. This clears up potential confusion with save_app.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

restore_appRestore an app versionA
Idempotent

Roll an app back to one of its earlier checkpoints: re-saves that checkpoint's HTML as a NEW current one (nothing is lost — history is preserved and you can roll forward again). Use when a newer edit broke the UI. Get the checkpoint number from app_history; after restoring, open_app to view it.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameYes
checkpointYeswhich checkpoint to restore, 1 = the oldest (see app_history)
command_idNoidempotency key (uuid); auto-generated if omitted

TDQS

A4.2/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations provide idempotentHint=true and destructiveHint=false; the description adds valuable context that the restore is non-destructive ('nothing is lost — history is preserved and you can roll forward again') and that it creates a NEW current version. This goes beyond structured metadata.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is concise, front-loading the core purpose, then adding workflow. The parenthetical about non-destructive behavior is useful but makes the sentence dense. Overall, every sentence earns its place.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a 3-parameter tool with no output schema, the description covers the action, non-destructive nature, usage trigger, prerequisite, and post-restore step. It is complete enough for an agent to select and invoke the tool correctly, especially with sibling context.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The schema covers 'checkpoint' (with description) and 'command_id', but 'name' remains undocumented. The description adds context for 'checkpoint' via app_history but does little to explain 'name' or further clarify command_id. Schema coverage is 67%, so the description only partially compensates.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool's function: rolling an app back to an earlier checkpoint by re-saving its HTML as a new current version. It distinguishes from siblings like app_history (which lists checkpoints) and open_app (which views), and clarifies it's non-destructive.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Provides explicit when to use ('when a newer edit broke the UI'), prerequisite ('Get the checkpoint number from app_history'), and follow-up action ('after restoring, open_app to view it'). Does not mention when-not or alternatives, but gives clear context.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

save_appSave appA
Idempotent

Create or update a UI app in the persistent registry. Two slots, each optional on update (an omitted slot keeps its current value): ui — the complete self-contained HTML document (contract in get_app_guide; window.oma, no external resources, NO embedded manifest block) — and manifest, the app's declaration as a JSON object (kind, collections, settings, scene; keys in get_app_guide). manifest: null clears the declaration. Creating needs ui. Every save snapshots both slots as one new version (history kept). After saving, open it IMMEDIATELY with open_app.

ParametersJSON Schema
NameRequiredDescriptionDefault
uiNocomplete self-contained HTML document using window.oma; omit on update to keep the current one
nameYesapp name, ^[a-z][a-z0-9-]{0,31}$ (e.g. 'kanban', 'habit-tracker')
manifestNodeclaration object (whole-value replace), null to clear, omit to keep
command_idNoidempotency key (uuid); auto-generated if omitted
descriptionNoone line: what this app shows and what data fields it uses
expected_versionNoREQUIRED when overwriting an existing app: the version you read (get_app). Creating a new name needs none

Output Schema

ParametersJSON Schema
NameRequiredDescription
okYes
eotNo
nameNo
noteNo
sizeNo
reasonNo
appliedNo
createdNo
versionNo
prev_sizeNo
manifest_actionNo
expected_versionNo

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

This goes far beyond the annotations. It discloses slot-merge semantics, manifest null clearing, snapshot creation for every save, history retention, and the required immediate open_app call. An agent understands the tool's side effects without experimentation.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Dense and front-loaded with the core purpose, then systematically covers slots, versioning, and next action. Every sentence earns its place and there is no filler or repetition of schema text.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a 6-parameter upsert with a rich schema and output schema, the description is complete: it covers create/update behavior, slot semantics, clearing, versioning, and the immediate next step. It also points to get_app_guide for contract details, leaving no material gap.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3. The description adds meaning by explaining the two-slot update model, the ui contract, manifest null behavior, and the 'creating needs ui' constraint. It does not expand on command_id or expected_version, but the schema already covers those clearly.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Create or update a UI app in the persistent registry.' It clearly distinguishes save_app from siblings like open_app and get_app by emphasizing slot-based updates, version snapshotting, and the required follow-up with open_app.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives clear operational context: omitted slots keep current values, creating requires ui, manifest null clears the declaration, and 'after saving, open it IMMEDIATELY with open_app.' It does not explicitly name exclusions or alternative tools such as edit_app or restore_app, so it stops short of a 5.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

security_setSet a security policy keyA
Idempotent

Privileged writer for reserved settings keys (security:* / policy:) — the ONLY tool that can write them; the generic data_ tools refuse reserved keys. Upserts one key/value in the settings collection.

ParametersJSON Schema
NameRequiredDescriptionDefault
keyYesa reserved key, e.g. security:kanban:send_message (cap suffixes are snake_case — the caps field names)
valueYesthe policy value: allow | deny (true/false too); delete_items also takes confirm; call_tools takes "*", a JSON array or a comma-separated tool list; policy:csp:<app> (or policy:csp:*) takes a JSON object of origin arrays, e.g. {"connectDomains":["https://api.example.com"]}. An unknown value is REFUSED, never stored
command_idNoidempotency key (uuid); auto-generated if omitted

Output Schema

ParametersJSON Schema
NameRequiredDescription
idNo
okYes
eotNo
seqNo
itemNo
noteNo
reasonNo
deletedNo
collectionNo
violationsNo
expected_versionNo
prev_collection_seqNo

TDQS

A4.5/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already cover idempotency and non-destructiveness; the description adds the privileged-auth requirement, the reserved-key restriction, and the upsert semantics in the settings collection. This goes beyond the structured annotations without contradicting them.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Two dense sentences carry the core purpose, exclusivity, and write behavior. The most important differentiator ('the ONLY tool that can write them') is front-loaded, with no filler.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the rich schema, an output schema, and annotations, the description provides the essential contextual framing: target keys, elevated privileges, exclusivity, and upsert behavior. Nothing needed for correct selection or invocation is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, and the schema itself provides detailed parameter semantics for key, value, and command_id. The tool description does not add parameter-level meaning, but with full schema coverage it does not need to.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb ('Privileged writer') and precise resource scope ('reserved settings keys (security:* / policy:*)'), and explicitly differentiates from the generic data_* tools. An agent can immediately understand both what it does and how it is distinct.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Explicitly names the alternative family (data_* tools) and explains the exclusion: data_* tools refuse reserved keys, so security_set is the ONLY writer for these keys. This gives the agent a clear routing rule.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

ui_prefs_schemaShared preference catalogA
Read-only

The engine-owned catalog of SHARED preferences (key, type, label, default, options) that the settings app renders. Apps read effective values via oma.pref(); this tool only describes what exists. Read-only.

ParametersJSON Schema
NameRequiredDescriptionDefault

No parameters

Output Schema

ParametersJSON Schema
NameRequiredDescription
sharedYes

TDQS

A4.4/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true, and the description reinforces this with 'Read-only' while adding context about engine ownership, the settings app rendering, and the boundary with oma.pref(). This adds useful behavioral context beyond the annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact and front-loaded, but the phrase 'Read-only.' is redundant given readOnlyHint=true. Still, both sentences earn their place by explaining ownership, rendering, and the oma.pref() distinction.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a zero-parameter read-only catalog tool with an output schema, the description is complete: it names the resource, the contents, the consumers, and the boundary against runtime value retrieval. Nothing essential is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The tool has zero parameters and schema description coverage is 100%, so there is no parameter information to add. The description still clarifies what the catalog entries contain (key, type, label, default, options), which helps an agent understand the output.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific verb ('describes') and resource ('engine-owned catalog of SHARED preferences'), and clearly distinguishes the tool from effective-value retrieval by noting that apps read values via oma.pref() while this tool only describes what exists.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies the intended use: inspect the catalog of shared preference definitions rather than read effective values. It explains the relationship to oma.pref(), though it does not explicitly name alternatives or state when not to use it.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Tool Schema Changelog

Recent tool additions, removals, and schema changes observed during successful MCP inspections. Dates show when Glama detected each change.

  1. 10 tool updatesv0.6.0
    • Changedapp_html1 field changed
      • addedOutput schema / properties / csp
        Added value: +{
        +  "additionalProperties": {
        +    "items": {
        +      "type": "string"
        +    },
        +    "type": "array"
        +  },
        +  "propertyNames": {
        +    "type": "string"
        +  },
        +  "type": "object"
        +}
    • Changeddata_collections2 fields changed
      • removedOutput schema / properties / collections / items / properties / last_activity / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedOutput schema / properties / collections / items / properties / last_activity / type
        Added value: +[
        +  "string",
        +  "null"
        +]
    • Changeddata_list2 fields changed
      • removedOutput schema / properties / next_cursor / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedOutput schema / properties / next_cursor / type
        Added value: +[
        +  "string",
        +  "null"
        +]
    • Changededit_app2 fields changed
      • removedOutput schema / properties / prev_size / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedOutput schema / properties / prev_size / type
        Added value: +[
        +  "number",
        +  "null"
        +]
    • Changedfile_list2 fields changed
      • removedOutput schema / properties / next_cursor / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedOutput schema / properties / next_cursor / type
        Added value: +[
        +  "string",
        +  "null"
        +]
    • Changedfile_read2 fields changed
      • removedOutput schema / properties / next_offset / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedOutput schema / properties / next_offset / type
        Added value: +[
        +  "number",
        +  "null"
        +]
    • Changedget_app2 fields changed
      • removedOutput schema / properties / next_offset / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedOutput schema / properties / next_offset / type
        Added value: +[
        +  "number",
        +  "null"
        +]
    • Changedsave_app2 fields changed
      • removedOutput schema / properties / prev_size / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedOutput schema / properties / prev_size / type
        Added value: +[
        +  "number",
        +  "null"
        +]
    • Changedsecurity_set1 field changed
      • changedInput schema / properties / value / description
        Previous value: -"the policy value: allow | deny (true/false too); delete_items also takes confirm; call_tools takes \"*\", a JSON array or a comma-separated tool list. An unknown value is REFUSED, never stored"New value: +"the policy value: allow | deny (true/false too); delete_items also takes confirm; call_tools takes \"*\", a JSON array or a comma-separated tool list; policy:csp:<app> (or policy:csp:*) takes a JSON object of origin arrays, e.g. {\"connectDomains\":[\"https://api.example.com\"]}. An unknown value is REFUSED, never stored"
    • Changedui_prefs_schema2 fields changed
      • removedOutput schema / properties / shared / items / properties / default / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "boolean"
        -  }
        -]
      • addedOutput schema / properties / shared / items / properties / default / type
        Added value: +[
        +  "string",
        +  "number",
        +  "boolean"
        +]

TDQS

A3.9/5.0
Disambiguation4/5

The domain prefixes and operational verbs make most tools clearly distinct, and the descriptions explicitly separate potentially confusing pairs like open_app vs data_list and save_app vs edit_app. A few internal helpers such as app_html and app_store_preview could be mistaken for user-facing tools, but their descriptions clearly mark them as internal.

Naming Consistency4/5

Most tools follow predictable prefix-plus-operation patterns such as data_add_item, file_write, app_store_list, and delete_app. However, a handful of noun-style names like app_html, app_history, data_changes, data_version, and ui_prefs_schema break the otherwise mostly consistent verb_noun convention.

Tool Count2/5

At 33 tools, this server exceeds the 25+ threshold and feels like a bundled multi-domain API rather than a tightly scoped MCP server. Each tool has a defensible purpose, but the heavy surface is likely to burden agents with unnecessary choice and would be better split into smaller focused servers.

Completeness4/5

The tool set covers app lifecycle (create, read, edit, delete, history, restore), data CRUD plus batch and change tracking, file CRUD plus chunked uploads, and app-store install/update workflows. Minor gaps exist, such as no direct generic preference-write tool and no dedicated single-item data read, but agents can work around these with data_list and save_app.

Maintenance

ActivityMaintained
ResponsivenessNo issues

Related MCP Connectors

Related MCP Servers

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/2nd1st/open-mcp-apps'

If you have feedback or need assistance with the MCP directory API, please join our Discord server