MCP reference
The @betterknow/appilot-mcp server is the tool surface behind the app-configurator skill.
It is a standard stdio MCP server, so any MCP-capable agent can mount it.
Environment
| Variable | Required | Meaning |
|---|---|---|
APPILOT_BASE_URL | yes for live calls | Backend URL, cloud (https://api.appilot.de) or on-premise |
APPILOT_PAT | for writes and the server-side echo | A scoped service token (appilot_pat_...) |
APPILOT_APP_ID | optional | Default app id for tools that omit one |
APPILOT_SOAK_STORAGE_STATE | optional | Path to a Playwright storageState JSON for an authenticated site session |
The server is endpoint-agnostic: the same binary serves cloud and on-premise
instances. Nothing is hard-coded to a host. It can start and expose tools before
these variables are supplied, but live calls report that APPILOT_BASE_URL is
not configured.
Tools
| Tool | Input | What it does |
|---|---|---|
capabilities | None | Instance version, migration level, schema versions, configurable entities. Call first. |
read_config | appId?, locales? | Normalized snapshot of the app's content model. |
validate_config | appId?, locales? | Severity-ranked findings against the health contract (runs locally, plus a server-side plan echo). |
update_action_plan | id, patch | Update a stored action plan; the server re-validates the marker trust boundary. |
update_control | id, patch | Update a control (e.g. replace an unstable locator). |
update_knowledge | id, patch | Update a knowledge article (scope, translations, remove filler). |
export_config | appId? | Export the whole configuration as a portable, versioned bundle (backup/clone artifact). Secrets never leave; the bundle carries references only. |
import_config | appId?, bundle, mode, dryRun?, expectedCurrentHash?, allowUnhealthy? | Import a bundle. Always dry-run first (the default): review the per-entity diff, then commit merge (upsert, never deletes) or replace (exact match, incl. deletions) with the dry-run's confirm hash. Every commit stores an automatic pre-restore snapshot, so any import can be undone. |
soak_selectors | url, appId? | Headless-browser check that each control selector resolves on the live page. Needs Playwright. |
Remote endpoint
Clients that cannot start a local program (ChatGPT, claude.ai) connect to a deployed endpoint instead. One deployment serves one Appilot instance and holds no credential of its own: each person who connects supplies their own service token, once, on a consent screen.
Run it from the built image:
pnpm -C packages/tools/appilot-mcp build
docker build -t appilot-mcp packages/tools/appilot-mcp
docker run -p 8080:8080 \
-e APPILOT_BASE_URL=https://api.appilot.de \
-e APPILOT_MCP_PUBLIC_URL=https://mcp.example.com \
-e APPILOT_MCP_OAUTH_SECRET="$(openssl rand -base64 32)" \
appilot-mcp
| Variable | Meaning |
|---|---|
APPILOT_BASE_URL | The instance this endpoint serves |
APPILOT_MCP_PUBLIC_URL | The public origin people reach, used in OAuth metadata and redirects |
APPILOT_MCP_OAUTH_SECRET | At least 32 characters. Rotating it disconnects every client |
APPILOT_MCP_ALLOWED_HOSTS | Optional extra Host values, comma separated, behind a proxy |
Clients discover everything else themselves: the MCP endpoint is
https://<host>/mcp, and the OAuth metadata sits at the usual well-known paths.
What a person sees is one screen asking for a service token, which the endpoint checks against your instance before granting anything. The scopes granted are the ones that token already carries, never more. To cut a connection off, revoke the token in the Backoffice: the next call fails.
The live soak tool is not available over the remote endpoint. Driving a real browser belongs on your own machine, over the local connection.
To connect ChatGPT to an instance with no public endpoint at all, use OpenAI's Secure MCP Tunnel against the local server instead. The tunnel dials out from inside your network, so nothing needs to listen on the internet.
Service-token scopes
| Scope | Grants |
|---|---|
config:read | Read, validate, and export configuration |
config:write | Apply fixes (create/update controls, forms, plans, knowledge) and import/restore bundles |
Mint tokens in the Backoffice (Admin → Service tokens). Only the hash is stored; the raw token is shown once. Tokens are org-scoped, optionally app-scoped, revocable, and can carry an expiry. A write attempt with a read-only token returns a clear scope error. Mint a write-scoped token rather than working around it.
Local vs live checks
- Static gate (
validate_config) runs entirely locally, with no public network required, reusing Appilot's own validators so it never drifts from the runtime. - Server echo re-runs the plan trust boundary without persisting.
- Live soak (
soak_selectors) drives the real page; it is the only check that catches an unstable selector before your users do.
Health contract
validate_config checks: plan actionability (a create flow must enter a value
and submit; a plan that stops at opening an element fails), single-executable-marker
steps, marker resolution, selector stability, scope/view_path consistency, i18n coverage,
knowledge scope and hygiene, procedure-not-in-KB, identifier hygiene, and plan
discovery. Findings are ranked critical → low; a configuration passes when it has
no critical or high findings.