mcpField
F
formio-mcp

formio-mcp

本地服务
form.io开发工具81 周前更新

关于 formio-mcp

formio-mcp 是用于从 MCP 客户端管理 Form.io 项目的 MCP 服务,适合通过 Agent 操作表单、角色和动作。它通过 stdio 提供 25 个工具,并支持项目配置及表单版本管理。

主要功能

  1. 01创建、查询和更新表单
  2. 02管理表单草稿与修订版本
  3. 03创建和更新项目角色
  4. 04管理表单动作
  5. 05配置 Form.io 项目

适用场景

  1. 01从 Agent 创建或更新表单
  2. 02查看并发布表单草稿
  3. 03管理项目角色与表单动作

MCP 相关

该服务通过 stdio 向 MCP 客户端提供 25 个 Form.io 工具;不提供 HTTP 或 SSE 传输。项目凭据可通过环境变量或项目配置提供。

配置

本地服务的配置在各客户端中通用,复制后粘贴到客户端的 MCP 配置文件即可。

mcp.json · 通用配置
{
"mcpServers": {
"io-form-formio": {
"command": "npx",
"args": [
"-y",
"@formio/mcp"
],
"env": {
"FORMIO_PROJECT_URL": "<FORMIO_PROJECT_URL>",
"FORMIO_BASE_URL": "<FORMIO_BASE_URL>",
"FORMIO_API_KEY": "<FORMIO_API_KEY>",
"FORMIO_LOGIN_FORM": "<FORMIO_LOGIN_FORM>",
"FORMIO_AUTH_HOST": "<FORMIO_AUTH_HOST>",
"FORMIO_AUTH_PORT": "<FORMIO_AUTH_PORT>",
"FORMIO_AUTH_TIMEOUT": "<FORMIO_AUTH_TIMEOUT>",
"FORMIO_FORCE_BROWSER": "<FORMIO_FORCE_BROWSER>",
"FORMIO_REQUEST_TIMEOUT": "<FORMIO_REQUEST_TIMEOUT>",
"FORMIO_INSECURE_TLS": "<FORMIO_INSECURE_TLS>"
}
}
}
}
启动命令npx -y @formio/mcp
需要配置的环境变量
FORMIO_PROJECT_URLOptional, and the WEAKEST of the three project sources: a committed formio.json found by walking up from the working directory wins, then the per-directory mapping project_set writes, then this. It pins nothing — project_set can redirect a directory whose environment names a different project. Useful for a launch with nowhere to record a project, such as CI or a container (e.g. https://examples.form.io on the hosted cloud; self-hosted it is either https://your-project.your-domain.com or https://your-host/project-name, depending on how that deployment routes projects). Leave it unset and the agent asks for a project and records it per directory.
FORMIO_BASE_URLOptional, and usually unnecessary: the base URL is DERIVED from the project URL — https://api.form.io for a project on a form.io host, the parent path for a project addressed as a sub-directory — and is asked for only when it cannot be derived, which is a path-less project URL on a customer domain. There is no default. Like FORMIO_PROJECT_URL it is the weakest source, behind a committed formio.json and the per-directory mapping.
FORMIO_API_KEY密钥Form.io project API key. Optional — applied only to the project FORMIO_PROJECT_URL names, so set FORMIO_PROJECT_URL beside it; any other project, and every project when it is omitted, uses the browser-based portal login flow to obtain a JWT.
FORMIO_LOGIN_FORMURL of a custom login form used by the browser-based portal login flow. Defaults to the deployment's portal login form.
FORMIO_AUTH_HOST密钥Address the browser-login page binds to. Optional; defaults to 127.0.0.1. Set it to 0.0.0.0, together with FORMIO_AUTH_PORT, when the server runs in a container or on a remote machine and the login page must be reachable through a published port. 0.0.0.0 exposes the page on every interface for the duration of a login.
FORMIO_AUTH_PORT密钥Fixed port for the browser-login page, so a container can publish it (e.g. 43117). Optional; a positive integer, and by default the page takes an ephemeral port.
FORMIO_AUTH_TIMEOUT密钥Seconds to wait for a browser login before the call fails with an error naming the remedies. Optional; a positive integer no larger than 2147483, and any other value is ignored. Defaults to 900.
FORMIO_FORCE_BROWSERSet to 1 to attempt the browser login even where the server detects it cannot present one (CI, a container, a remote shell with no display). Use it when the login page is reachable from a browser elsewhere.
FORMIO_REQUEST_TIMEOUTSeconds a Form.io request may go unanswered before the call fails with a network error naming the URL. Optional; a positive integer no larger than 2147483, and any other value is ignored. Defaults to 60. project_import and project_export wait 300 seconds, or this value when it is longer.
FORMIO_INSECURE_TLSSet to 1 to skip TLS certificate verification only for requests to the configured deployment (the hosts of the resolved project URL and base URL); every other host is verified as usual. For local development against self-signed certificates only — never enable in production.

本地服务需要在你的电脑上安装运行环境(如 Node.js 18+)。各客户端的配置文件位置不同,请参考客户端文档。

安装包
npm@formio/mcp1.0.1

工具

21

收录的工具列表 · 更新于 2 周前

参数类型必填说明
namestring否要问候的姓名

详细介绍

Formio MCP 服务

npm: @formio/mcp Smithery MCP Registry

MCP 服务(@formio/mcp)可独立供任何支持 MCP 的客户端使用。它使用 stdio:客户端负责启动它,并管理 stdin/stdout。无需开放端口,也无需手动启动任何内容。

从此仓库的克隆版本中,入口点是 src/stdio.ts:

pnpm install
pnpm --filter @formio/mcp exec tsx src/stdio.ts

这样运行时,它会等待 stdin 上的 MCP 流量;这只能说明它可以正常启动——应改为让客户端调用该命令。构建后的软件包会将同一入口点作为 formio-mcp 可执行文件和 dist/stdio.js 提供。

传输方式
传输方式命令兼容客户端
stdionpx -y @formio/[email protected](或 node dist/stdio.js)Claude Code、Claude Desktop、Cursor、VS Code、Codex、Windsurf、Cline——任何通过 stdio 使用 MCP 的客户端

不支持 HTTP 或 SSE 传输。该服务唯一的 HTTP 监听器是身份验证中所述的临时浏览器登录页面,不承载任何 MCP 流量。

连接客户端

同一个 stdio 入口适用于所有客户端,但配置文件的位置以及所在的键名会因客户端而异:Claude Code 使用 mcpServers 下的 .mcp.json,Cursor 使用 mcpServers 下的 .cursor/mcp.json,VS Code 使用 servers 下的 .vscode/mcp.json,Codex 则使用 TOML 格式的 .codex/config.toml。不存在通用的 .mcp.json。根 README列出了各客户端的完整配置表;JSON 的 mcpServers 格式如下:

{
  "mcpServers": {
    "formio-mcp": {
      "command": "npx",
      "args": ["-y", "@formio/[email protected]"],
      "env": {
        "FORMIO_PROJECT_URL": "https://your-project.form.io"
      }
    }
  }
}

每个访问 Form.io 的工具都需要一个项目。项目可以来自已提交的 formio.json、由 project_set 工具写入的目录映射,或环境中的 FORMIO_PROJECT_URL;顺序按作用范围从窄到宽,因此映射会覆盖环境变量,而已提交的文件会覆盖两者。FORMIO_BASE_URL 是可选的,通常不需要:系统会根据项目 URL 的形式推导基础 URL——位于 form.io 主机上的项目使用 https://api.form.io,通过子目录路由的项目则使用其父路径;只有在无法推导时才会要求提供。没有任何插件清单会提示输入这两个值;每个客户端都会通过 project_set 或已提交的 formio.json 按目录记录这些值。.mcpb 桌面套件是唯一例外,因为桌面主机没有可供交互配置的工作目录。

即使这两个值都未设置,服务也能启动,因此客户端可以先连接并列出工具,再进行配置——只有在工具需要项目 URL 时才会要求提供,而 server_status 始终可用。

在 Docker 中运行

该服务提供 Dockerfile,并以 formio/mcp 的名称发布到 Docker Hub,支持 linux/amd64 和 linux/arm64。该镜像使用 stdio,因此 MCP 客户端负责管理 stdin/stdout,容器必须使用 -i 运行:

docker run -i --rm \
  -e FORMIO_PROJECT_URL=https://your-project.form.io \
  -e FORMIO_API_KEY=your-api-key \
  formio/mcp

接入客户端时——与连接客户端使用相同的入口,只需将 command 和 args 指向 Docker——配置如下(此处展示 JSON 的 mcpServers 格式;如上所述,VS Code 使用 servers,Codex 使用 TOML):

{
  "mcpServers": {
    "formio-mcp": {
      "command": "docker",
      "args": [
        "run", "-i", "--rm",
        "-e", "FORMIO_PROJECT_URL",
        "-e", "FORMIO_API_KEY",
        "formio/mcp"
      ],
      "env": {
        "FORMIO_PROJECT_URL": "https://your-project.form.io",
        "FORMIO_API_KEY": "your-api-key"
      }
    }
  }
}
容器中的身份验证

推荐使用 FORMIO_API_KEY,无需浏览器,也无需交互操作。发布身份验证端口后,也可以通过浏览器登录;这两种方式请参阅无头环境。

无论采用哪种身份验证方式,都有两点容器专属注意事项。优先使用 FORMIO_PROJECT_URL 环境变量,而不是 project_set 工具:project_set 会将每个目录的映射持久化到 ~/.formio/projects.json,该文件位于容器内,会在容器退出时被丢弃。此外,每个工具接受的 cwd 参数都指向容器内的路径,而非主机上的路径;客户端报告的工作区根目录则是主机路径,因此请显式传入 cwd。

要在多次容器运行之间复用令牌,请挂载缓存目录。该目录必须可写,因为令牌刷新或清除时,服务会重写文件:

-v "$HOME/.formio:/root/.formio"
自托管部署

部署未公开时,通常会遇到以下两个问题:

主机名解析。 容器内无法解析私有主机名。请显式映射:

docker run -i --rm --add-host forms.internal:10.0.0.5 \
  -e FORMIO_BASE_URL=https://forms.internal \
  -e FORMIO_PROJECT_URL=https://forms.internal/my-project \
  -e FORMIO_API_KEY=your-api-key \
  formio/mcp

私有或自签名证书。 此镜像仅信任标准 CA 证书包。即使主机通过 macOS 钥匙串等方式信任某个证书,该证书在容器内仍会验证失败,工具会只显示 fetch failed。有两种情况,处理方式各不相同:

由私有 CA 签发。 挂载 CA 证书,并将 Node 指向该证书:

-v /path/to/rootCA.pem:/certs/rootCA.pem:ro -e NODE_EXTRA_CA_CERTS=/certs/rootCA.pem

完全自签名的服务器证书——其主题与颁发者相同,且没有 CA:TRUE 基本约束。NODE_EXTRA_CA_CERTS 无法解决此问题,即使挂载服务器自己的证书也不行:Node 要求信任锚必须是 CA,并会以 DEPTH_ZERO_SELF_SIGNED_CERT 错误拒绝证书链。使用以下命令确认属于哪种情况:

echo | openssl s_client -connect your-host:443 -servername your-host 2>/dev/null \
  | openssl x509 -noout -subject -issuer

如果主题与颁发者相同,唯一的选择是使用 FORMIO_INSECURE_TLS=1。它只会对发往已配置部署的请求跳过证书验证;服务访问的其他所有主机仍会进行验证。仅用于本地开发,切勿用于生产部署。

在本地构建镜像

构建上下文是仓库根目录,而不是当前目录:镜像使用仓库的 pnpm-lock.yaml 安装依赖,并启用冻结锁文件,因此镜像中包含的版本与仓库测试过的版本完全一致。请在仓库根目录运行:

docker build -f packages/mcp-server/Dockerfile -t formio-mcp .
使用 MCP Inspector 检查

MCP Inspector 可连接到服务,让你手动浏览和调用其工具 — 在将配置接入 Agent 前,可用它确认配置是否正常。启动 Web 门户:

npx @modelcontextprotocol/inspector

它会打印一个带有身份验证令牌的 URL 并打开浏览器。默认端口为 6274;如果该端口已被占用,可将两者改为 CLIENT_PORT=6284 SERVER_PORT=6285。

将 inspector-config.json 导入 MCP Inspector,连接服务,并针对真实项目调用 form_list

将 inspector-config.example.json 复制为 inspector-config.json,填入项目 URL 和 API 密钥,就得到了下一步所需的文件。该文件名已添加到 gitignore 中,因此填好内容的副本不会被意外提交。

同一流程的逐步说明:

1. 选择 Add Servers → Import from client config。

Add Servers 菜单,其中高亮显示 Import from client config

2. 点击“From file…”。 对话框接受客户端配置文件或这台机器上已安装的客户端 — 没有可粘贴 JSON 的位置。

Import from client config 对话框,提供客户端下拉菜单和 From file 按钮

**3. 选择你的 inspector-config.json,**其中定义的服务会列为新增服务。点击“Import 1 server”确认。

对话框在 New servers 下列出 formio-mcp,并提供 Import 1 server 按钮

4. 使用服务卡片上的切换开关启用服务。 容器启动后,开关会变为绿色并显示协商后的协议版本;首次连接较慢,因为 Docker 需要启动容器。

formio-mcp 的服务卡片显示 Connected,以及它运行的 docker 命令

5. 打开 Tools 选项卡,查看此服务提供的工具。每个服务都会列出全部 25 个工具 — 包括为每个客户端注册的 project_set 和 project_get。

Tools 选项卡列出服务的 Form.io 工具

6. 选择一个工具,填写参数,然后点击“Execute Tool”。 结果会显示在中间窗格中,JSON-RPC 交互则显示在右侧的 Protocol 面板中。server_status 不会访问凭据,也不会发出 Form.io 请求,因此可用于区分传输问题和身份验证问题;下方的 form_list 则会针对项目发起真实调用。

form_list 结果显示从 Form.io 项目返回的表单定义

导入会将服务写入 Inspector 自己的目录 ~/.mcp-inspector/mcp.json,因此下次使用时它仍会保留 — 用完后可从服务卡片中移除。如果某个工具只报出 fetch failed,通常是部署问题,而非服务问题:请参阅可自托管部署,了解容器内的主机名解析和证书信任。


MCP 服务工具

捆绑的 @formio/mcp 服务提供以下 25 个工具。只要操作有对应工具,技能就会优先使用它们,而不是原始 HTTP。

表单
工具用途
form_create创建新表单。先使用 formio-schema 技能构建 JSON 定义。在支持修订版本的部署中,revisions 默认为 "original"。
form_get根据 _id 或路径(formIdOrPath)获取单个表单定义。draft: true 则获取其草稿。
form_list分页列出表单,可按 type 和 tags 筛选(表单需包含给出的所有标签)。除非 select 指定其他字段,否则返回摘要字段。
form_update使用编辑后的 JSON 更新表单。先调用 form_get,使用 formio-schema 编辑,然后更新。draft: true 会保存草稿,而不是当前生效的表单。
form_publish将表单草稿发布为当前生效版本(formId、note)。表单没有草稿时会失败并返回 NO_DRAFT。需要修订版本许可证(Security Module)。
form_revert将先前修订版本的组件、标签、属性和显示设置还原到当前生效的表单(formId、version、note)。需要修订版本许可证(Security Module)。
form_revision_list按时间倒序列出表单的修订版本摘要(_id、_vid、_vnote、_vuser、created、modified)。需要启用表单修订版本。
form_revision_get根据 _vid 或修订版本文档 _id 获取单个不可变的表单修订版本。
角色
工具用途
role_create创建新的项目角色,参数为 role: { title, description?, default?, admin? }。
role_list分页列出项目角色。
role_update更新角色(roleId、role)。未提供的字段会保留已存储的值。
操作
工具用途
action_type_list列出服务上所有可用的操作类型——完整目录,Form.io 不会对其分页。
action_type_get获取操作类型的设置架构。目录中没有列出的类型会失败并返回 UNKNOWN_ACTION_TYPE。
action_create向表单添加新操作。
action_list分页列出表单上的操作。
action_get根据 ID 获取单个操作。
action_update更新操作。未提供的字段会保留已存储的值。
action_delete从表单中移除操作。
项目
工具用途
project_export将项目的完整模板(角色、资源、表单、操作)导出为可移植的 JSON 文档。指定 tag 时,导出存储在该版本标签中的模板——工作区的 template.json 刷新方式即是如此。
project_import导入模板 JSON 以进行首次构建。模板中列出的每个表单都会在原位置替换,其操作会被删除并重新创建;模板中的 access 会替换项目的 access;未列出的表单、角色和操作会保留。使用表单、角色和操作工具更改现有项目。
project_tag_list列出项目的当前版本及其版本标签,按时间从新到旧排列。使用 compare: true 时,列出自当前版本以来发生变更的角色、资源、表单和操作。
project_tag_create为项目创建版本:Form.io 会将其当前状态保存为带有 description 的 semver tag。
project_get报告目录解析到哪个项目、哪个部署主机托管该项目,以及各项信息来自哪个层级。这是在首次调用读取或写入工具前应运行的预检。它在服务内部使用与其他工具相同的解析器返回结果,因此无需运行 shell 命令。返回的 status 为 ok、not-configured 或 base-url-unresolved。
project_set将目录的 Project URL 保存到 ~/.formio/projects.json。若要将目标与代码一同记录,请在应用自身文件夹中编写并提交 formio.json——服务会读取该文件,但绝不会写入该文件。一个服务可为多个工作区提供服务。此映射会应用于对应目录及其下的所有子目录,直到遇到首个包含 .git 的文件夹——这与搜索 formio.json 时使用的边界相同,因此父文件夹上的映射不会延伸到其下克隆的代码仓库中;当工作目录位于多个已映射文件夹中时,以最近的已映射文件夹为准。此处写入的映射会覆盖服务环境中的 FORMIO_PROJECT_URL,后者的优先级最低。
project_set 为什么采用这种方式

工具的描述只包含调用方需要遵循的规则。背后的原因如下:

  • 调用本身就是持久化操作。 Agent 如果只在文本中回答“切换到项目 X”,实际上什么也没改变;只有工具调用才能写入映射。
  • 映射以调用解析到的目录为键。 如果传入了 cwd,就是该目录;否则就是其他工具解析到的同一目录(参见下文的约定)。唯一固定的是最后的回退值——服务进程自身的工作目录,它在客户端启动服务时确定,而且通常不是用户当前工作的目录,因此以该目录为键写入映射就会造成这种情况。
  • 无需重启,但映射不一定始终生效。 每个工具都会在每次调用时解析项目,因此下一次调用就会读取新映射。只有在映射是实际生效记录的情况下,它才会起作用:如果存在已提交的 formio.json,映射会在该文件消失时作为回退值。这就是为什么结果会报告实际解析出的那一对值(projectUrl、ok),而不是刚刚记录的值。
  • 基础 URL 是推导出来的,不需要询问。 它用于构造门户登录 URL,并作为缓存令牌的键;因此,错误的基础 URL 会导致登录失败,而不是请求失败;猜测出的基础 URL 则会将登录请求发送到用户并未使用的部署。对于 form.io 主机(https://api.form.io,所有托管项目共用的基础 URL)和子目录项目(父路径),基础 URL 都可以推导出来。例外情况是客户域名上没有路径的项目 URL:其部署位于同级子域名,而项目 URL 中没有任何信息能指出该子域名。
  • 部署与项目绑定。 基础 URL 会按目录存储在与之关联的项目旁边,因此每个目录都可以指向不同的部署,而且任何部署都不会响应其他项目的请求。因此,若某次调用将目录重新指向另一个项目,就不会保留基础 URL:旧值属于被替换的项目。
  • 映射仅限本机。 映射以绝对路径为键,因此克隆后不会保留。已提交的 formio.json 会进行版本控制、显示在差异中,并与克隆仓库的所有人共享,因此当目标属于应用时,优先使用它。
  • 拒绝未知参数。 输入架构是严格的:工具不接受的参数(例如已移除的 scope)会被拒绝,而不是直接丢弃,因此根据旧文档编写的调用不会错误地报告一项实际未发生的写入。
诊断
工具用途
server_status报告服务的名称和版本,以及 cwd 如何解析到项目,与 project_get 相同。它不会发出 Form.io 请求,也不需要凭据,因此可用于区分传输问题和身份验证或配置问题——其他工具失败时请先调用它。
每个工具都遵循的约定
  • cwd. 每个解析项目的工具都接受可选的 cwd,并在每次调用时按以下顺序为一个目录进行解析:cwd 参数;客户端的工作区根目录(当客户端声明了 MCP roots 能力时)——只有一个根目录时直接使用;有多个根目录时,由包含项目记录(已提交的 formio.json 或目录映射,包括损坏的映射)的根目录决定;如果它们都包含相同的记录,则使用其中第一个;如果都不包含记录,则使用下一个来源;如果包含不同记录,则拒绝并返回列出这些根目录的 INVALID_ARGUMENT;绝对路径的 CLAUDE_PROJECT_DIR 环境变量;最后是服务进程自身的工作目录,即客户端启动服务时所在的目录。每个会话开始时读取一次根目录,并在收到 notifications/roots/list_changed 后再次读取;如果 roots/list 失败或在 2 秒内没有响应,则继续使用上一次成功读取的列表;只有从未成功读取过时才视为没有根目录。project_get 和 server_status 会通过 cwdSource 报告来源(argument、client-root、claude-project-dir 或 server)。当 cwdSource 为 server 或 claude-project-dir 时(这两者都是对用户所在位置的猜测),请传入绝对路径形式的 cwd;如果要指定其他目录,也请传入 cwd,例如在 monorepo 中指定某个应用,而每个应用都有自己的 formio.json。
  • formId 和 formIdOrPath。 formId 始终是表单的 24 字符 ObjectId _id。formIdOrPath 接受 _id 或表单路径,且仅用于 Form.io 按路径提供的读取操作:form_get、form_revision_list 和 form_revision_get。如果将路径作为 formId 传入,则会以 INVALID_ARGUMENT 拒绝;请使用 form_get 读取表单的 _id。
  • 列表。 form_list、role_list、action_list 和 form_revision_list 接受 limit(默认值为 100)、skip、sort 和 select。每个操作都会在各自的键(forms、roles、actions、revisions)下返回条目,并同时返回 total(整个查询匹配的条目数)和 hasMore(如果还有下一页则为 true):请增大 skip 再次调用,直到 hasMore 为 false。如果 Form.io 未报告总数,则不返回 total;当返回的页面已满时,hasMore 为 true。action_type_list 以相同方式返回 actionTypes,且 hasMore 始终为 false。
  • 更新会覆盖发送的内容。 form_update、role_update 和 action_update 会发送 PUT 请求,由 Form.io 将其应用于已存储的文档:请求体中的每个字段都会覆盖已存储的对应字段,而未包含的顶层字段会保留其已存储的值。请求体中的数组或对象会按原样存储,即整个替换已存储的内容,而不是与之合并,因此请发送该字段应保留的所有组件、访问条目或设置。
  • 修订历史。 如果 form_create 或 form_update 保存时不会保留修订历史(部署未获得修订功能许可、请求体将 revisions 设为 "",或更新目标表单已关闭修订功能),则会以 HISTORY_NOT_ACCEPTED 拒绝且不会写入任何内容,除非调用传入 acceptNoHistory: true。服务本身绝不会提示用户:Agent 会转达拒绝信息,并根据用户的答复重试。草稿、form_publish 和 form_revert 需要修订功能许可;没有许可时会以 LICENSE_REQUIRED 拒绝。
  • 错误。 调用失败时会返回 isError: true,文本以方括号中的错误代码开头([NOT_FOUND] …),后接错误消息;同时返回 _meta["io.form/error"]: { code, status?, body? },其中 status 是 Form.io 的 HTTP 状态码,body 是其响应正文,截断至 2,000 个字符。错误结果不包含 structuredContent。错误代码包括 NOT_CONFIGURED、BASE_URL_UNRESOLVED、CONFIG_UNREADABLE、INVALID_ARGUMENT、AUTH_REQUIRED、FORBIDDEN、NOT_FOUND、VALIDATION_FAILED、LICENSE_REQUIRED、HISTORY_NOT_ACCEPTED、NO_DRAFT、UNKNOWN_ACTION_TYPE、REDIRECTED、UPSTREAM_ERROR、NETWORK_ERROR 和 INTERNAL。不符合工具输入架构的参数会由 MCP SDK 以纯文本报告,不带错误代码。

身份验证

MCP 服务支持两种身份验证模式:

  • JWT 模式(默认)。 一个短期运行的本地 Express 服务会呈现 Form.io 门户登录表单;用户登录一次后,JWT 会通过 /callback 端点返回,formioFetch 会在之后的每个请求中附加 x-jwt-token。此流程是隐式的——缓存未命中时,首次经过身份验证的工具调用会触发登录。不存在显式的 authenticate 工具。
  • API 密钥模式。 在 FORMIO_PROJECT_URL 旁设置 FORMIO_API_KEY 环境变量。对项目 FORMIO_PROJECT_URL 的请求会附加 x-token,并完全跳过浏览器流程;任何由已提交的 formio.json 或目录映射解析出的其他项目,则会通过门户登录进行身份验证,project_get 会说明原因。

JWT 会缓存在 ~/.formio/mcp-tokens.json 中(模式为 0600),并以解析后的 Base URL 为键——同一部署上的所有项目共用一个令牌。令牌的有效期约为七天;命中缓存时,服务会在本地检查是否过期,然后向服务器重新验证;如果任一检查失败,则会重新登录。

授予 Agent 的权限。 JWT 模式会将登录者的 JWT交给 Agent,因此在令牌有效期内,Agent 将以该用户的权限执行操作——如果以管理员身份登录,Agent 就会继承对该部署的管理员访问权限。API 密钥则仅限于其所属项目。对于无人值守或共享环境,建议使用 API 密钥模式;使用 JWT 模式时,请以权限最低的用户身份登录。

无头环境

默认情况下,登录页面会在绑定到 127.0.0.1 的临时端口上提供,服务会直接启动默认浏览器,而不通过 shell:macOS 使用 open,Linux 使用 xdg-open,Windows 使用 url.dll 协议处理程序——这要求同一台机器上有桌面浏览器。

如果不满足这一条件——例如在容器、SSH 会话或 CI 中——你有以下三种选择:

  1. 在 FORMIO_PROJECT_URL 旁设置 FORMIO_API_KEY 环境变量,完全跳过浏览器。最适合无人值守使用。

  2. 手动完成登录。 每次尝试登录时,都会在尝试启动浏览器之前将登录 URL 写入 stderr——不只是出错时才写入。如果启动失败,系统会额外输出一行说明,而不会将错误吞掉。该 URL 也会出现在超时错误中,客户端会将其作为工具输出展示,因此即使你看不到服务日志,也能获取该 URL。

    使用 stderr 是因为采用 stdio 传输时,stdout 承载的是 MCP 协议本身——向其中写入其他内容会破坏数据流。

  3. 绑定到可访问的地址。 将 FORMIO_AUTH_HOST=0.0.0.0 和 FORMIO_AUTH_PORT 设为固定的已发布端口,然后从你自己的机器打开 URL:

    docker run -i --rm -p 43117:43117 \
      -e FORMIO_PROJECT_URL=https://your-project.form.io \
      -e FORMIO_AUTH_HOST=0.0.0.0 -e FORMIO_AUTH_PORT=43117 \
      formio/mcp
    

    FORMIO_AUTH_HOST=0.0.0.0 会在登录期间将登录页面暴露到所有网络接口。只有在可以接受的情况下才使用此设置。

无论通过哪种方式访问,都请按打印的原样打开登录 URL,包括其中的 ?s= 值:页面仅针对该值提供服务,该值会在每次登录时生成。通过转发端口访问(例如 devcontainer、Codespaces)时,请保留 ?s= 值,只更改主机和端口。

如果在 FORMIO_AUTH_TIMEOUT 秒内(默认值为 900)没有收到登录请求,调用会失败并返回说明这些选项的错误,而不是一直挂起直到客户端放弃。

登录表单自动解析

未设置 FORMIO_LOGIN_FORM 时,服务会在首次登录尝试时探测以下候选地址,并缓存第一个有响应的地址(每个候选地址的超时为 1.5 秒):

  1. {baseUrl}/formio/user/login(门户基础地址)
  2. {projectUrl}/admin/login(项目管理员)
  3. {projectUrl}/user/login(项目用户)

{baseUrl} 和 {projectUrl} 是解析后的值——即 project get 为该目录报告的值——而不是名称相似的环境变量。

此探测会延迟执行——只有实际提供本地身份验证页面时才会运行。


环境变量

名称必需默认值用途托管式 SaaS 示例自托管示例
FORMIO_PROJECT_URL是*—Form.io 项目的完整 URL。三个来源中优先级最低:从工作目录向上查找时找到的已提交 formio.json 优先,其次是由 project_set 写入的目录映射,最后才是此变量。对于自托管部署,它是部署的子目录或自有域名的子域名(https://myproject.example.com),具体取决于该部署如何路由项目。https://myproject.form.iohttps://forms.example.com/myproject
FORMIO_BASE_URL否根据说明推导Form.io 部署的完整基础 URL。通常由项目 URL 推导,而不是手动设置——对于位于 form.io 主机上的项目,该值为 https://api.form.io;对于通过子目录寻址的项目,该值为父路径。仅当项目 URL 是自有域名上没有路径的地址,且无法从部署中推导时才设置此变量。三个来源中优先级最低:已提交的 formio.json 优先,其次是目录映射,最后才是此变量。在托管云上,该值始终为 https://api.form.io,而不是项目的 *.form.io 子域名。https://api.form.iohttps://forms.example.com
FORMIO_API_KEY否undefined长期有效的项目 API 密钥,仅应用于 FORMIO_PROJECT_URL 指定的项目——请同时设置 FORMIO_PROJECT_URL。适用时,服务会跳过浏览器登录流程——这是在没有浏览器的主机上进行身份验证的唯一方式。CHANGEMECHANGEME
FORMIO_LOGIN_FORM否自动解析覆盖 JWT 登录流程使用的门户登录表单 URL。https://formio.form.io/user/loginhttps://forms.example.com/formio/user/login
FORMIO_AUTH_HOST否127.0.0.1浏览器登录页面的绑定地址。0.0.0.0 可使其从容器外部访问。
FORMIO_AUTH_PORT否临时端口浏览器登录页面使用的固定端口,以便容器可以发布该端口。4311743117
FORMIO_AUTH_TIMEOUT否900等待浏览器登录的秒数,超时后调用将失败。必须是大于 0 且不超过 2147483 的整数;其他值将被忽略。
FORMIO_REQUEST_TIMEOUT否60Form.io 请求等待响应的秒数,超时后调用将失败,并返回包含 URL 和等待时长的 NETWORK_ERROR。必须是大于 0 且不超过 2147483 的整数;其他值将被忽略。project_import 和 project_export 会等待 300 秒;如果此变量设置的时间更长,则使用该值。
FORMIO_INSECURE_TLS否undefined设置为 1 可仅对发往已配置部署(已解析的 Project URL 和 Base URL 所属主机)的请求跳过 TLS 验证;其他所有主机仍按常规方式验证。仅用于本地开发——绝不可用于生产环境。
FORMIO_FORCE_BROWSER否0设置为 1,即使服务检测不到浏览器(CI、容器、没有显示器的 SSH 环境),也尝试进行浏览器登录。
* 非启动时要求——服务器会启动、列出所有工具,并在没有它的情况下响应 server_status;只有读取或写入 Form.io 数据的工具会报错,并指出 project_set 和此变量。替代方案是 project_set 工具,它会将工作目录映射到 ~/.formio/projects.json 中的一个项目。解析按作用域进行,从最窄范围开始:从调用方的 cwd 向上查找时找到的已提交 formio.json,然后是 cwd 或其最近映射的祖先目录对应的映射,接着是环境中的 FORMIO_PROJECT_URL(优先级最低),最后才报错。在任何客户端连接之前,先用 npx -y @formio/[email protected] project set --project-url <url> --cwd <path> 映射目录——只要能从项目 URL 推导出部署地址,系统就会自动推导,因此只有当服务器提示无法确定时才添加 --base-url <url>。在两个 URL 参数旁添加 --force,即可记录一组不符合域名规则的 URL——规则唯一无法判断是误操作的情况,是部署在 *.form.io 域名下的内部部署;这两个 URL 必须在同一次调用中提供,此设置会在之后的每次读取中生效,并且这是仅限 Shell 使用的标志,project_set 工具不支持它。project set --reset --cwd <path> 会清除目录的条目,这也是取消强制设置的方法:如果一次写入没有更改这两个值,则会保留该覆盖设置,因此取消强制后再记录不会产生任何变化。project get --cwd <path> 会打印解析结果以及胜出的来源。解析成功时退出码为 0;该目录没有映射时退出码为 1;命令无法给出结果时退出码为 2(例如用法错误、URL 格式错误、无法读取 ~/.formio/projects.json);项目已解析但无法确定其 Base URL 时退出码为 3——这样调用方就能区分“这里尚未配置”“操作失败”和“配置了一半,且缺少以下值”。project set --cwd <path> 在目录已准备好处理调用时退出码为 0;仍缺少指定值时退出码为 1;命令无法给出结果时退出码为 2;记录已写入但目录仍无法解析出 Base URL 时退出码为 3——已提交的 formio.json 会优先控制该目录,但没有提供 Base URL,因此应修改该文件,而不是再次写入。

CLI 参考:project get、project set 和 project logout

formio-mcp 二进制文件(npx -y @formio/[email protected] project …)会报告某个目录解析到的内容,并在任何客户端连接之前为该目录记录项目。project logout 会退出一个部署的登录状态——即该目录解析到的部署(解析方式与 project get 完全相同),或由 --base-url 指定的部署——方法是从 ~/.formio/mcp-tokens.json 中删除该部署缓存的令牌,同时保留所有其他条目。正在运行的服务会在下次调用时检测到这一变化并重新登录,因此退出登录或切换账户无需重启。这些标志和退出代码属于 1.0 版的接口。

标志命令含义
--cwd <absolute path>全部三个命令要报告、记录或退出登录的目录。默认为当前目录;不接受相对路径。
--project-url <url>project set要记录的 Project URL。
--base-url <url>project set托管该项目的部署。仅当服务表示无法从 Project URL 推导出此地址时才传入。
--forceproject set按照给定内容原样记录这一对值,跳过域名检查。要求在同一次调用中同时提供 --project-url 和 --base-url。project_set 工具没有对应选项。
--resetproject set清除此目录在 ~/.formio/projects.json 中的条目。不接受 URL。
--base-url <url>project logout要退出登录的部署,替代 --cwd 所解析到的部署。
退出代码project getproject setproject logout
0该目录解析到了一个项目及其 Base URL。该目录已准备好处理调用。令牌已删除,或该部署没有缓存令牌;输出会说明是哪种情况。
1未为该目录映射任何内容。仍缺少一个已指定的值。未为该目录映射任何内容,因此无法解析出部署;请使用 --base-url 指定一个部署。或者,给定的 --base-url 不是有效 URL;请重新索取。
2命令无法作出判断:用法错误、URL 格式错误,或无法读取 ~/.formio/projects.json。命令无法作出判断。命令无法作出判断:用法错误,或无法读取或写入 ~/.formio/mcp-tokens.json。
3已解析出项目,但无法确定其 Base URL。记录已写入,但该目录仍无法解析出 Base URL:已提交的 formio.json 对其生效且未提供 Base URL,因此需要编辑该文件。已解析出项目,但无法确定其部署;请使用 --base-url 指定部署。

隐私政策

Form.io 的隐私政策涵盖此服务连接的 Form.io 服务:https://form.io/privacy

此服务自身如何处理数据,以下内容说明了上述政策无法描述的部分:

您的数据会去往何处。 仅发送至您配置的 Form.io 部署。每个请求都会发送至为您的工作目录解析出的 Project URL 和 Base URL — 您自己的 SaaS 项目或自托管服务。自托管时,此服务不会向 Form.io 发送任何内容,也不会进行任何形式的遥测、分析或使用情况报告。

您的机器上存储了什么。 ~/.formio/ 下的两个文件,写入时的权限均为 0600:

文件内容写入时机
mcp-tokens.json浏览器登录获得的 JWT,以解析出的 Base URL 为键您通过浏览器登录时
projects.json每个目录对应的项目和基础 URL 映射运行 project_set 时

表单数据和提交内容绝不会写入磁盘 — 它们仅在内存中传递,用于响应工具调用。

凭据。 设置 FORMIO_API_KEY 环境变量后,此服务会从环境中读取该变量,并且仅在向名称为 FORMIO_PROJECT_URL 的项目发出请求时,将其作为身份验证标头发送;该变量绝不会写入磁盘。缓存的 JWT 有效期约为 7 天,之后此服务会重新进行身份验证。删除 ~/.formio/mcp-tokens.json 可立即退出登录。

第三方。 此服务不会联系任何第三方服务。有一个例外值得说明:浏览器登录页面由本地提供,而该页面所加载的 Form.io 渲染器及其样式表来自 cdn.jsdelivr.net,网页字体来自 fonts.googleapis.com,Form.io 徽标来自 portal.form.io,因此这些主机在该页面打开期间会看到您的浏览器 IP 地址。页面上的其他所有内容均来自您自己的部署。在 FORMIO_PROJECT_URL 旁设置 FORMIO_API_KEY 环境变量,即可完全跳过浏览器登录流程,避免上述情况。

保留期限。 上述文件会一直保留,直到您将其删除。Form.io 项目中的数据遵循您自己的部署所设定的保留规则;对于托管在 Form.io 上的项目,则遵循上方链接中的政策。

有关数据处理的问题,请联系:[email protected]

评论

支持 Markdown

第一次接触 MCP?

从协议是什么,到在客户端里装上第一个服务,这几条回答覆盖了大多数入门问题。

一个开放协议,规定了 AI 应用如何以统一方式连接外部工具与数据源。客户端负责与模型对话,MCP 服务负责提供工具、资源和提示模板,两者通过标准消息通信,同一个服务可以被不同客户端复用。