Logo
热心市民王先生

技术原理核心

技术研究 WebMCP 浏览器API

WebMCP协议的技术架构、核心组件与设计哲学

协议定位:从MCP到WebMCP

Anthropic MCP回顾

Model Context Protocol(MCP)由Anthropic于2024年11月推出,是一种基于JSON-RPC的协议标准,用于连接AI模型与外部工具和数据源。MCP采用服务器中心架构:

┌─────────────┐    JSON-RPC    ┌─────────────┐
│  AI Client  │ ◄────────────► │  MCP Server │
│  (Claude)   │   stdio/HTTP   │  (Backend)  │
└─────────────┘                └─────────────┘

MCP服务器作为独立进程或托管服务运行,AI客户端通过stdio、HTTP with SSE等传输协议连接。这种架构适合后端集成场景——连接文件系统、数据库、API和企业服务。

WebMCP的架构创新

WebMCP的核心洞察是:网页本身就是一个活的、已认证的、有状态的运行时。用户在场、会话活跃、JavaScript已拥有应用暴露的所有能力。与其通过独立服务器路由,不如让页面直接向浏览器声明自己的工具。

graph TB
    subgraph Browser
        A[Web Page / Tab] --> B[navigator.modelContext]
        B --> C[Tool Registry]
    end
    
    subgraph Agent
        D[AI Agent] --> E[Tool Discovery]
        E --> F[Tool Invocation]
    end
    
    F --> B
    C --> G[Execute in Page Context]
    G --> H[Return Structured Result]
    H --> D

WebMCP使网页成为MCP服务器的客户端侧实现——工具在客户端脚本中执行而非后端。

核心API表面

WebMCP扩展浏览器的Navigator接口,新增只读属性:

navigator.modelContext  // ModelContext对象

访问限制:仅在安全上下文(HTTPS)中可用。

ModelContext接口方法

方法描述
provideContext(options)原子性地注册一组工具,替换之前所有注册
clearContext()清除当前页面所有已注册工具
registerTool(tool)添加单个工具,不清除已有注册
unregisterTool(name)按名称移除特定工具

工具定义结构(ModelContextTool)

{
  name: "searchProducts",           // 必需,唯一标识符
  description: "搜索产品目录...",    // 自然语言描述
  inputSchema: {                    // JSON Schema,可选
    type: "object",
    properties: {
      query: { type: "string" },
      category: { type: "string" },
      maxPrice: { type: "number" }
    },
    required: ["query"]
  },
  execute: async (inputs, client) => {   // 必需,执行回调
    // 工具在页面JS上下文中执行,拥有完整会话访问权限
    const results = await searchCatalog(inputs);
    return { content: [{ type: "text", text: JSON.stringify(results) }] };
  },
  annotations: {
    readOnlyHint: true    // 建议:此工具不修改状态
  }
}

人机交互确认机制

execute回调接收ModelContextClient对象作为第二个参数,提供requestUserInteraction(callback)方法:

execute: async (inputs, client) => {
  await client.requestUserInteraction(async () => {
    // 用户确认后执行此回调
    await processCheckout(inputs.cartId);
  });
  return { content: [{ type: "text", text: "结账完成" }] };
}

这是敏感操作的主要人机确认关口。

两种集成路径

声明式API(Declarative API)

无需JavaScript,通过HTML属性注解现有表单:

<form
  id="support-ticket-form"
  toolname="createSupportTicket"
  tooldescription="提交新的客户支持工单"
  toolautosubmit="true"
>
  <input
    type="text"
    name="issueTitle"
    required
    toolparamtitle="问题标题"
    toolparamdescription="问题简要描述"
  />
  <textarea
    name="description"
    toolparamtitle="详细描述"
    toolparamdescription="问题的详细描述"
  ></textarea>
  <select name="severity">
    <option value="low"></option>
    <option value="high"></option>
    <option value="critical">紧急</option>
  </select>
</form>

关键属性

  • toolname(必需):工具标识符
  • tooldescription(必需):工具功能描述
  • toolautosubmit(可选):代理填充后自动提交
  • toolparamtitle / toolparamdescription:字段注解

SubmitEvent.agentInvoked布尔标志区分人工提交和代理提交,便于服务端差异化处理。

命令式API(Imperative API)

适用于非表单操作、多步骤工作流、动态工具注册:

navigator.modelContext.registerTool({
  name: "filterProducts",
  description: "按品牌、评分和库存筛选产品",
  inputSchema: {
    type: "object",
    properties: {
      brands: { type: "array", items: { type: "string" } },
      minRating: { type: "number", minimum: 0, maximum: 5 },
      inStockOnly: { type: "boolean" }
    }
  },
  execute: async ({ brands, minRating, inStockOnly }, client) => {
    await applyProductFilters({ brands, minRating, inStockOnly });
    const count = document.querySelectorAll('.product-card').length;
    return {
      content: [{
        type: "text",
        text: `筛选完成,共${count}个匹配产品`
      }]
    };
  }
});

两种API的选择策略

场景推荐方案
现有HTML表单,输入定义清晰声明式
表单提交触发服务端操作声明式 + toolautosubmit
非表单操作(登出、导航、自定义触发)命令式
多步骤工作流,有中间状态命令式
基于应用状态动态注册工具命令式
最大兼容性,最小JS开销声明式

设计哲学

为什么是浏览器原生而非后端代理

  1. 会话继承:工具在已认证的浏览器会话中执行,无需单独的凭证管理。

  2. 零部署成本:无需维护独立的MCP服务器,无需后端API包装层。

  3. 实时状态:页面本身就是有状态的运行时,工具可以访问最新的应用状态。

  4. 安全边界清晰:浏览器执行同源策略、权限策略,提供原生安全隔离。

与后端MCP的互补关系

WebMCP并非替代后端MCP,而是解决不同层面的问题:

协议层面适用场景
MCP后端工具集成直接API调用、企业服务集成、无用户在场场景
WebMCP客户端浏览器工具暴露浏览器代理交互、继承用户会话、前端业务逻辑

一个复杂的代理任务可能同时使用两种协议:通过MCP连接数据库,通过WebMCP操作第三方Web界面。