跳转至

代理支付执行(x402)

通过策略门控支付和内置支出控制,启用 AI 代理。使用 x402 HTTP 支付协议和 MCP 工具,您可以在无托管风险的情况下向外部服务、API 或其他代理付款。

何时使用

在以下情况下使用:当代理需要为 API 调用付费、购买服务、与其他代理结算、强制执行按任务的支出限制,或管理非托管钱包时。它可以与 cost-aware-llm-pipeline 和 security-review 技能自然结合。

决策树

根据代理是购买访问付费 API,还是向他人收取访问费用,选择集成路径:

需求 推荐路径
代理向 Base 或其他支持 agentwallet 的链上的 402 门控 API 付款 使用 agentwallet-sdk 作为 MCP 支付服务器,并采用严格的支出策略
代理向 X Layer 的 402 门控 API 付款 使用 okx/onchainos-skills 中的 OKX 代理支付协议;okx-x402-payment 是已弃用的旧版别名
TypeScript API 向代理收费 使用面向 Express、Hono、Fastify 或 Next.js 的 OKX Payments TypeScript 卖家 SDK 文档
Go API 向代理收费 使用面向 Gin、Echo 或 net/http 的 OKX Payments Go 卖家 SDK 文档
Rust API 向代理收费 使用面向 Axum 的 OKX Payments Rust 卖家 SDK 文档
Java API 向代理收费 使用面向 Spring Boot 2/3、Java EE 或 Jakarta 的 OKX Payments Java 卖家 SDK 文档
Python API 向代理收费 在实现前检查当前 OKX Payments 仓库;可能没有 Python 卖家指南

支持的网络

  • agentwallet-sdk: 在生产使用前,通过包文档确认当前网络覆盖范围。Base Sepolia 是最安全的开发默认值;Base 主网是原始技能中描述的生产路径。
  • OKX Payments / X Layer: 当前卖家文档面向 X Layer(eip155:196)和 USDT0 支付。由于支付包和协调器的行为可能快速变化,请在生成生产代码前获取当前 SDK 文档。

工作原理

x402 协议

x402 将 HTTP 402(Payment Required)扩展为机器可协商的流程。当服务器返回 402 时,代理的支付工具会协商价格、确认预算、对交易签名,并且仅在编排器设置的策略和确认边界内重试。

支出控制

所有支付工具调用都会强制执行 SpendingPolicy: - 按任务预算 — 单个代理操作的最大支出 - 按会话预算 — 整个会话的累计限制 - 允许列表中的收款人 — 限制代理可以支付的地址/服务 - 速率限制 — 每分钟/每小时的最大交易数

非托管钱包

代理通过 ERC-4337 智能账户保留自己的密钥。编排器在委托前设置策略,代理只能在边界内支出。没有池化资金,没有托管风险。

MCP 集成

支付层公开标准 MCP 工具,可集成到 Claude Code 或代理框架的设置中。

安全注意: 请始终固定包版本。此工具管理私钥 — 未固定的 npx 安装会带来供应链风险。

选项 A: agentwallet-sdk(Base / 多链)

{
  "mcpServers": {
    "agentpay": {
      "command": "npx",
      "args": ["agentwallet-sdk@6.0.0"]
    }
  }
}

可用工具(代理可调用)

工具 目的
get_balance 查看代理钱包余额
send_payment 向地址或 ENS 发送支付
check_spending 查询剩余预算
list_transactions 所有支付的审计痕迹

注意: 支出策略由编排器在委托给代理之前设置 — 而不是由代理本身设置。这可以防止代理升级自己的支出限制。通过 set_policy 在编排层或任务前钩子中设置策略,不要将其作为代理可调用工具。

选项 B: OKX 代理支付协议(X Layer)

对于 X Layer x402、多方支付(MPP)、会话支付、计费、A2A 计费流程,请使用此路径。

对于买方代理流程:

  1. 安装或引用当前的 okx/onchainos-skills 仓库。
  2. 将 skills/okx-agent-payments-protocol/SKILL.md 用作调度器。
  3. 将 skills/okx-x402-payment/SKILL.md 视为已弃用的兼容别名,不要将其作为正式技能。
  4. 在检查钱包状态或执行支付操作之前,请求明确的用户确认。不要在通用工具调用背后隐藏支付执行。

对于卖方 API 流程,请在生成代码前获取最新的语言特定指南:

运行时 当前指南
TypeScript https://raw.githubusercontent.com/okx/payments/main/typescript/SELLER.md
Go https://raw.githubusercontent.com/okx/payments/main/go/x402/SELLER.md
Rust https://raw.githubusercontent.com/okx/payments/main/rust/x402/SELLER.md
Java https://raw.githubusercontent.com/okx/payments/main/java/SELLER.md

不要在没有检查当前 OKX 仓库的情况下复制旧文档中的示例。当前 OKX 指南将 okx-agent-payments-protocol 用作调度器,并且 Java 卖家文档已可用。

示例

MCP 客户端中的预算强制执行

在构建编排器以在分发付费工具调用之前强制执行预算时使用。

前提条件: 在添加 MCP 配置之前安装包 — 在非交互式环境中,不带 -y 的 npx 会请求确认,导致服务器挂起:npm install -g agentwallet-sdk@6.0.0

import { Client } from "@modelcontextprotocol/sdk/client/index.js";
import { StdioClientTransport } from "@modelcontextprotocol/sdk/client/stdio.js";

async function main() {
  // 1. トランスポートを構築する前に認証情報を検証する。
  //    キーが欠落している場合は即座に失敗する — 認証なしでサブプロセスを開始させない。
  const walletKey = process.env.WALLET_PRIVATE_KEY;
  if (!walletKey) {
    throw new Error("WALLET_PRIVATE_KEY is not set — refusing to start payment server");
  }

  // stdio トランスポートを介して agentpay MCP サーバーに接続する。
  // サーバーが必要とする env 変数のみをホワイトリストに登録する —
  // 秘密鍵を管理するサードパーティのサブプロセスに process.env のすべてを渡さない。
  const transport = new StdioClientTransport({
    command: "npx",
    args: ["agentwallet-sdk@6.0.0"],
    env: {
      PATH: process.env.PATH ?? "",
      NODE_ENV: process.env.NODE_ENV ?? "production",
      WALLET_PRIVATE_KEY: walletKey,
    },
  });
  const agentpay = new Client({ name: "orchestrator", version: "1.0.0" });
  await agentpay.connect(transport);

  // 2. エージェントへの委任前に支出ポリシーを設定する。
  //    常に成功を確認する — サイレントな失敗はコントロールがアクティブでないことを意味する。
  const policyResult = await agentpay.callTool({
    name: "set_policy",
    arguments: {
      per_task_budget: 0.50,
      per_session_budget: 5.00,
      allowlisted_recipients: ["api.example.com"],
    },
  });
  if (policyResult.isError) {
    throw new Error(
      `Failed to set spending policy — do not delegate: ${JSON.stringify(policyResult.content)}`
    );
  }

  // 3. 有料アクションの前に preToolCheck を使用する
  await preToolCheck(agentpay, 0.01);
}

// プレツールフック: 4 つの異なるエラーパスを持つフェイルクローズドバジェット強制。
async function preToolCheck(agentpay: Client, apiCost: number): Promise<void> {
  // パス 1: 無効な入力を拒否する(NaN/Infinity は < 比較をバイパスする)
  if (!Number.isFinite(apiCost) || apiCost < 0) {
    throw new Error(`Invalid apiCost: ${apiCost} — action blocked`);
  }

  // パス 2: トランスポート/接続の失敗
  let result;
  try {
    result = await agentpay.callTool({ name: "check_spending" });
  } catch (err) {
    throw new Error(`Payment service unreachable — action blocked: ${err}`);
  }

  // パス 3: ツールがエラーを返した(例:認証失敗、ウォレット未初期化)
  if (result.isError) {
    throw new Error(
      `check_spending failed — action blocked: ${JSON.stringify(result.content)}`
    );
  }

  // パス 4: レスポンスの形状を解析して検証する
  let remaining: number;
  try {
    const parsed = JSON.parse(
      (result.content as Array<{ text: string }>)[0].text
    );
    if (!Number.isFinite(parsed?.remaining)) {
      throw new TypeError("missing or non-finite 'remaining' field");
    }
    remaining = parsed.remaining;
  } catch (err) {
    throw new Error(
      `check_spending returned unexpected format — action blocked: ${err}`
    );
  }

  // パス 5: バジェット超過
  if (remaining < apiCost) {
    throw new Error(
      `Budget exceeded: need $${apiCost} but only $${remaining} remaining`
    );
  }
}

main().catch((err) => {
  console.error(err);
  process.exitCode = 1;
});

最佳实践

  • 在委派前设置预算: 生成子智能体时,通过编排层附加 SpendingPolicy。不要赋予智能体无限制的支出权限。
  • 固定依赖: 在 MCP 配置中始终指定精确版本(例如:agentwallet-sdk@6.0.0)。在生产部署前确认软件包的完整性。
  • 审计轨迹: 在任务后钩子中使用 list_transactions 记录使用了哪些内容。
  • 失败关闭: 如果无法访问支付工具,则阻止付费操作 — 不要回退到未计费的访问。
  • 与 security-review 结合使用: 支付工具具有高权限。应用与 shell 访问相同的严格审查。
  • 先在测试网测试: 开发使用 Base Sepolia;生产切换到 Base 主网。

生产参考

本页原文 Markdown:在 AtomGit 查看·内容源自开源项目 ev/ECC