# Glippy WebMCP – a coding-agent plugin for making a site usable by browser agents

> Source: <https://github.com/jbobbink/glippy-webmcp>
> Published: 2026-08-27 11:33:40+00:00

Make a website usable by browser agents — with tools wired to the code you already have, not to the shape of your pages.

[WebMCP](https://github.com/webmachinelearning/webmcp) lets a page hand a browser agent
typed tools through `document.modelContext`

, so the agent acts through your own logic
instead of guessing at your DOM. This repository is a coding-agent plugin that audits what
your site could expose, writes those tools against real seams in your codebase, proves each
one works in a real browser, and publishes the manifests that let agents find them.

**MIT end to end. No vendor SDK. No telemetry** — the runtime makes no network request other
than the ones your own tools declare, and a test fails the build if that stops being true.

**Claude Code**

```
/plugin marketplace add glippy-dev/glippy-webmcp
/plugin install glippy-webmcp@glippy-dev
```

**Codex**

```
codex plugin marketplace add glippy-dev/glippy-webmcp
codex plugin add glippy-webmcp
```

Then, in your own project, ask your agent to audit the site's agent readiness.

Four skills, one arc:

| Skill | What it does |
|---|---|
`auditing-agent-readiness` |
Read-only. Produces a coverage table of user intents against the tools that exist — including the intents that are not worth building. Writes nothing at all. |
`implementing-webmcp-tools` |
Generates tools behind a hard human approval gate, wiring each to the highest available seam. |
`verifying-webmcp-tools` |
Executes every tool against the real site in a real browser and marks it verified, failed, or could-not-verify. Failed never ships. |
`publishing-agent-manifests` |
Emits the four artifacts that let agents discover your tools even where WebMCP is unsupported. |

Inventory a codebase first and you get forty candidate tools, on a page where Chrome's own guidance says an agent starts choosing worse above about twenty. Supply-first auditing is how a site ends up keyword-stuffed with tools nobody calls.

So the audit establishes what people actually try to do on the site, *then* inventories the
seams, and matches only at the end. The row it exists to be able to print is
`SKIP — no demand`

.

Each tool takes the highest rung available, because the rung decides whether it still works after the next redesign:

**An exported client function**— already typed and exercised by your UI.** An HTTP route the client already calls**— stable across restyles, and if the route validates its body, your input schema was written by someone who knew the answer.**A form**— including the declarative target, marked experimental because the spec section describing it says, verbatim,*"This section is entirely a TODO."***Recorded DOM steps**— works on anything, breaks on the next redesign.

WebMCP has no consent primitive. `requestUserInteraction()`

does not exist in the spec
repository at HEAD, despite Chrome's documentation referring to it. So nothing in the
platform stops a browser agent from calling a tool that charges a card.

This repository enforces it instead, as an error rather than a convention: an irreversible action must be gated by a confirmation in handoff mode, or end at a terminal navigation that returns control to your own UI. A warning sentence in a tool description is not a gate.

Actions are classified **by effect, not by HTTP verb** — a `GET`

that starts a checkout
session is a write — and `readOnlyHint`

is derived from the step graph rather than trusted
from the author, so a tool that writes cannot describe itself as safe.

| Package | |
|---|---|
`@glippy/webmcp-flow` |

`@glippy/webmcp`

`plugin/`

The expression resolver is a path walker, not an evaluator: no `eval`

, no `new Function`

.
A flow document is fetched over the network and inlined into your page, so anything that
could execute arbitrary text would be a remote-execution primitive aimed at your visitors.
It also means the runtime works under `script-src 'self'`

with no `unsafe-eval`

.

The surface is `document.modelContext`

— a `partial interface Document`

. The string
`navigator`

appears zero times in the specification at HEAD; `navigator.modelContext`

is a
2025 alias that survives only as a deprecated fallback in polyfills. Code written against
it silently finds nothing.

Tool names are 1–128 characters of `[A-Za-z0-9_.-]`

— that is normative, and violating it
throws `InvalidStateError`

. The ~30-character figure that circulates is Chrome ergonomics
guidance, so this repository treats it as a warning and never as an error.

For local development: `chrome://flags/#enable-webmcp-testing`

.

```
pnpm install
pnpm test        # packages + the plugin hook
pnpm typecheck
pnpm lint
```

[MIT](/jbobbink/glippy-webmcp/blob/main/LICENSE).
