@celilo/mcp
v0.5.1
Published
Celilo MCP service — drives a remote celilo server over the typed SSH API (@celilo/core runRemoteClient) via the Model Context Protocol. Dual read-only / read-write principals; tool surface derived from the server's live command registry.
Readme
@celilo/mcp
Operator-facing Model Context Protocol server that drives a remote celilo
server (celilo-mgr) over celilo's typed SSH Remote API, so an MCP client (e.g.
Claude Code) can operate the fleet with structured tools instead of screen
scraping. Design: openspec/changes/celilo-mcp-service/proposal.md.
Not to be confused with
@celilo/mcp-server— a separate dev/ops MCP server for orchestrating cele2e e2e runs.
Install
Node ≥ 20 only — no bun, no build step, no global install. @celilo/mcp
publishes as a single self-contained bundle, so point your MCP client at it with
npx:
# Claude Code — stdio server, fetched + run on demand
claude mcp add celilo -- npx -y @celilo/mcpPrerequisite: the celilo server already exposes the Remote API (the celilo-api
account + api-serve forced command). Then configure and enroll auth
(below), and run celilo api grant … once on the server.
Configure (two items — D1)
server (host/IP or a ~/.ssh/config alias) + defaultUser. These map onto
the Remote API dest <defaultUser>@<server>. Anything richer (port, IdentityFile,
ProxyJump) lives once in ~/.ssh/config.
Set via ~/.config/celilo-mcp/config.json:
{ "server": "celilo-mgr", "defaultUser": "peba" }…or env (CELILO_MCP_SERVER, CELILO_MCP_USER), which override the file.
Enroll auth (dual principal — D2)
celilo-mcp auth setupGenerates two ed25519 keypairs on this host (private keys never leave it):
| Principal | Grant | Used for |
|---|---|---|
| celilo-mcp-ro | read verbs | every read tool |
| celilo-mcp-rw | * | every mutating tool |
It prints the exact celilo api grant … lines to run once on the server —
the MCP server cannot self-authorize; grants are minted server-side by an
operator, like SSH.
Run
Your MCP client launches it for you (see Install). To drive it directly:
npx -y @celilo/mcp # stdio MCP server
npx -y @celilo/mcp auth setup # enroll the RO/RW principalsTool surface (generated live — D3)
On connect the server fetches the connected celilo's command registry
(celilo commands --json) and its configured providers (service list
--json) over the RO principal, then generates the tool surface from them — so
it mirrors whatever version celilo-mgr runs, never a compiled-in copy.
- One tool per runnable leaf, grouped by top-level command:
celilo_status,celilo_module_list,celilo_module_deploy,celilo_proxmox_node_list, … Each tool's input schema comes from the leaf's positional args + flags. - Read/write routing (D2). Every tool is tagged read-only or mutating (by its authz verb) and routed through the RO or RW principal accordingly.
celilo_run— a generic escape hatch that runs any validated argv (["module","list"]), routed read/write by the command verb.- Auto-detect. Provider-gated groups stay hidden until their service is
configured (no Proxmox service → no
celilo_proxmox_*). The server re-detects on a timer and emitsnotifications/tools/list_changedwhen the surface changes, so a live session updates without reconnecting.
A coverage gate (tests/coverage.test.ts) asserts every registry leaf maps to a
tool, so the surface can't silently drift from the API.
Grounding — resources & prompts (D5)
Resources give the model context, not actions:
| URI | Kind | Source |
|---|---|---|
| celilo://docs/subsystems | shipped doc | CELILO_SUBSYSTEMS.md — how modules deploy + the capability system |
| celilo://docs/core-modules | shipped doc | CELILO_CORE_MODULES.md — each module's provides/requires/role |
| celilo://docs/glossary | shipped doc | GLOSSARY.md — zones, the three internal senses, natIp |
| celilo://live/modules | live (RO) | module list |
| celilo://live/capabilities | live (RO) | capability list |
| celilo://live/status | live (RO) | status |
| celilo://live/events | live (RO) | events tail --limit 20 |
The shipped docs are versioned with the CLI so the grounding never drifts. They
resolve from the monorepo by default; set CELILO_MCP_DOCS_DIR to override.
Prompts are guided multi-step workflows (composition lives here, not in a
mega-tool): deploy-a-module, troubleshoot-failed-deploy, upgrade-npm-modules,
upgrade-apt-packages, assess-fleet-health.
