cloudflare/claude-managed-agents

GitHub: cloudflare/claude-managed-agents

Cloudflare 官方的 Claude Managed Agents 自托管控制平面,用于在 Cloudflare 上编排、沙箱化运行并扩展 AI Agent。

Stars: 247 | Forks: 41

# 在 Cloudflare 上运行 Claude Managed Agents 在 Cloudflare 上运行 Claude Managed Agents (CMA)。 本仓库提供了一个可自定义的控制平面,允许您: - 在完整容器和轻量级 isolate 上运行 CMA 沙箱 - 自定义您的 agent 使用的容器大小和镜像 - 获得对 agent 沙箱更好的可观测性 - 应用自定义的出站控制以实现[零信任凭证注入](https://blog.cloudflare.com/sandbox-auth/),并通过 [Workers VPC](https://developers.cloudflare.com/workers-vpc/) 连接到私有服务 - 使用 [Cloudflare 开发者平台](https://workers.cloudflare.com/products#all),通过 [Browser Run](https://developers.cloudflare.com/browser-run)、[Email](https://developers.cloudflare.com/email-service/) 以及任何其他自定义工具来扩展您的 Agent 您的需求。 请按照[入门指南](#onboarding-guide)开始操作。我们支持两种 部署方式:一键部署到 Cloudflare 按钮(基于 git,在 Workers Builds 中运行)以及从您的笔记本电脑执行的基于终端的 `npm run deploy` 流程。 ## 概述 本仓库部署了一个基于 Workers 的控制平面,用于在 Cloudflare 上运行 Claude Managed Agents。 当 agent 会话开始或结束时,Claude Managed Agents 会向您的 Worker 发送 webhook。控制平面会为每个会话启动一个沙箱,在会话休眠期间同步状态,并在会话结束时关闭沙箱。 沙箱可以是 [Cloudflare Containers](https://developers.cloudflare.com/containers/),也可以是使用 [AgentsSDK](https://developers.cloudflare.com/agents/) 的 [Isolate](https://developers.cloudflare.com/dynamic-workers/) 沙箱。这允许您要么获得 Linux VM 的完整功能,要么获得一个轻量级的 isolate,它可以在没有微 VM (microVM) 的资源开销和成本的情况下实现大规模扩展。 您可以配置策略来限制 agent 访问特定域名,在不让 agent 访问机密的情况下将凭证注入到传出请求中,或者编写任意代理代码来修改、重新路由或记录出站流量。 此外,您可以将 [Workers VPC](https://developers.cloudflare.com/workers-vpc/) 和 [Mesh](https://developers.cloudflare.com/workers-vpc/examples/connect-to-cloudflare-mesh/) 资源连接到您的沙箱。这允许您轻松访问任何云端或本地部署的私有资源,而无需将它们暴露给公共互联网。 最后,可以轻松扩展此代码库,以便向您的 agent 沙箱添加自定义工具。工具会被两种后端自动拾取,并在拥有 Worker 绑定的直接访问权限的情况下运行,从而可以利用整个 Cloudflare 开发者平台。 该仓库提供了以下内置工具: - 发送电子邮件 - 访问私有服务 - 浏览器自动化 - 图像生成 所有这些都可以通过部署到您 Cloudflare 账户的 UI 和 API 进行访问。 借助这个代码仓库,您应该能够快速建立并运行一个基于 Cloudflare 的自托管环境。然后您可以将其 fork,根据您的需求进行自定义并重新部署。此仓库旨在作为一个起点。 ## 入门指南 顺序很重要 —— 请按从上到下的步骤操作。 ### 选择部署方式 有两种部署方式。请选择一种,并在整个入门过程中坚持使用: - **基于 Git**。点击 [Deploy to Cloudflare](#step-1-initial-deploy) 按钮。 Cloudflare 会将此仓库 fork 到您的 GitHub 账户中,部署您的控制平面,然后未来向此 GitHub 仓库推送的更新将自动进行部署。 - **基于终端**。在您的笔记本电脑上运行 `npm run deploy`。需要 Docker(用于构建容器镜像)和 `wrangler login` 会话。 **两种途径在第 1 步和第 3 步有所不同** —— 下文为每种途径提供了 单独的小节。无论您如何部署,第 2 步以及第 4 步到第 9 步都是完全相同的。 ### 第 1 步. 初始部署 #### 基于 Git Deploy to Cloudflare 按钮会将此仓库 fork 到您的 GitHub 账户中, 自动配置 D1 数据库、KV 命名空间、R2 存储桶和 Durable Objects, 提示您输入所需的机密(见第 2 步),并 通过 Workers Builds 部署 Worker。 部署完成后,您将获得一个 `https://.workers.dev` URL,您将在第 2 步中需要它。 [![Deploy to Cloudflare](https://deploy.workers.cloudflare.com/button)](https://deploy.workers.cloudflare.com/?url=https://github.com/cloudflare/claude-managed-agents) 在完成剩余步骤之前,Worker 将无法运行。 #### 基于终端 ``` npm run deploy ``` `npm run deploy` 会构建您的基础沙箱容器镜像(需要 Docker),部署 Worker,并通过 `postdeploy` 钩子应用 D1 迁移。提交的 `wrangler.jsonc` 故意将 KV `id` 字段和 D1 `database_id` 留空 —— `scripts/ensure-kv.mjs` 和 `scripts/ensure-d1.mjs` 会在 `prebuild` 时运行,并将真实的 ID 修补进去(会采用按名称已存在的任何命名空间/数据库, 否则就创建全新的)。R2 存储桶按名称绑定(无需查找 ID),并由 wrangler 自动创建。 如果您登录的 Cloudflare 账户有权访问多个 账户,请在运行前设置 `CLOUDFLARE_ACCOUNT_ID`,以便确保 脚本知道要与哪个账户通信: ``` export CLOUDFLARE_ACCOUNT_ID= npm run deploy ``` 在完成剩余步骤之前,Worker 将无法运行,但是 部署过程会为您提供 Webhook 所需的 `https://.workers.dev` URL。 ### 第 2 步. 创建 Anthropic 环境和 webhook 在 [Claude Platform Console](https://platform.claude.com/workspaces/default/environments) 中创建一个“自托管”环境, 并保存环境密钥。然后,在 [Webhooks 设置](https://platform.claude.com/settings/workspaces/default/webhooks)中, 将 webhook URL 设置为 `https://.workers.dev/webhooks` 并保存生成的 Webhook Secret。 您将需要以下值: - `ENVIRONMENT_ID` —— 您的新自托管环境的 ID - `ANTHROPIC_ENVIRONMENT_KEY` —— 控制平面用于验证来自指定 Claude agent 环境的调用所使用的 环境密钥 - `ANTHROPIC_API_KEY` —— Worker 用来调用 Anthropic 的密钥 - `WEBHOOK_SECRET` —— 标准 Webhooks 签名密钥。Anthropic 将事件发布到您的 Worker;我们在对它们执行任何操作之前会 验证签名。 ### 第 3 步. 设置机密 #### 基于 Git Deploy to Cloudflare 表单在您部署时已提示输入核心机密,因此 `ENVIRONMENT_ID`、`ANTHROPIC_ENVIRONMENT_KEY` 和 `ANTHROPIC_API_KEY` 已经在您的 Worker 上。如果没有, 请使用 `npx wrangler secret put` 添加它们。 有两个后续操作: 1. **重新添加 `WEBHOOK_SECRET`。** 在您部署时 Webhook 尚未存在(您是在第 2 步中创建的),所以无论您在表单中 提供了什么占位符都是错误的。现在推送真实值: npx wrangler secret put WEBHOOK_SECRET 2. **将机密值复制到 `.dev.vars` 以进行本地开发。** Workers Builds 不会将您的表单输入同步回仓库,因此 否则 `wrangler dev` 将无法看到它们。 cp .dev.vars.example .dev.vars # 编辑 .dev.vars 并粘贴你在表单中提供的值, # 以及来自第 2 步的真实 WEBHOOK_SECRET。 #### 基于终端 设置本地开发: ``` cp .dev.vars.example .dev.vars # 使用你的真实值进行编辑 ``` 在生产环境中,`.dev.vars` 中的每个条目都需要匹配的 `wrangler secret put NAME`。四个核心机密是: ``` npx wrangler secret put ENVIRONMENT_ID npx wrangler secret put ANTHROPIC_ENVIRONMENT_KEY npx wrangler secret put ANTHROPIC_API_KEY npx wrangler secret put WEBHOOK_SECRET ``` ### 第 4 步. 应用 D1 迁移 `postdeploy` 钩子会在每次 `npm run deploy`(包括 Deploy to Cloudflare 按钮的部署)之后自动运行 `wrangler d1 migrations apply DB --remote`, 因此在生产环境方面无需执行任何操作。对于本地开发: ``` npm run db:migrate # local ``` ### 第 5 步. 配置 R2 快照凭证 R2 存储桶本身已在第 1 步中自动创建。生产环境中使用的 presigned-URL 路径仍然需要一个访问密钥。如果您在 Deploy to Cloudflare 表单期间提供了 `R2_ACCESS_KEY_ID` / `R2_SECRET_ACCESS_KEY` / `BACKUP_BUCKET_NAME` / `CLOUDFLARE_ACCOUNT_ID`,您可以 直接跳过 —— 它们已经设置好了。 除非您专门使用 Isolate 沙箱 或运行无状态的 agent 会话,否则这是必需的。Isolate 会话通过 Durable Object SQLite 存储进行持久化,不需要 R2 —— 如果您确定 永远不会运行 MicroVM agent,则可以跳过此步骤(并从 `wrangler.jsonc` 中删除 `r2_buckets` 块)。 任何运行 MicroVM 后端的人都应将此视为核心 入门步骤。 [生成一个 R2 访问密钥](https://dash.cloudflare.com?to=/:account/r2/api-tokens/create?type=user) ,拥有对 `claude-managed-agents-snapshots` 存储桶的读写权限 (Cloudflare dashboard → R2 → Manage R2 API Tokens → Create token), 复制 Access Key ID 和 Secret Access Key,然后推送 以下机密: ``` npx wrangler secret put R2_ACCESS_KEY_ID npx wrangler secret put R2_SECRET_ACCESS_KEY npx wrangler secret put BACKUP_BUCKET_NAME # same as bucket_name in wrangler.jsonc (IE: claude-managed-agents-snapshots) npx wrangler secret put CLOUDFLARE_ACCOUNT_ID # found in your dashboard URL ``` 有关更多信息,请参阅[快照和状态持久化](./docs/snapshots-and-state-persistence.md)。 ### 第 6 步.(可选)开启额外功能 Browser Rendering、Workers AI 和发送电子邮件功能都是开箱即用地配置好的 —— 如果您不需要,请在 `wrangler.jsonc` 中禁用它们。VPC 绑定 是选择加入的。 | 功能 | 默认 | 绑定 | 要添加的机密 | 设置步骤 | |---|---|---|---|---| | Browser Rendering 工具 | 开启 | `wrangler.jsonc` 中的 `browser` | `CLOUDFLARE_API_TOKEN`(用于 REST 工具) | 无 | | Workers AI 图像生成 | 开启 | `wrangler.jsonc` 中的 `ai` | 无 | 无 | | 发送电子邮件 + 收件箱 | 开启 | `wrangler.jsonc` 中的 `send_email`;设置 `EMAIL_DOMAIN` + `EMAIL_FROM`(Deploy to Cloudflare 会提示输入这些内容,或者在本地使用 `wrangler.jsonc` 中的 `vars`) | 无 | [Email 文档](./docs/agent-email.md) | | VPC 私有服务 | 关闭 | 在 `wrangler.jsonc` 中添加 `vpc_services` 块 | 无 | [Workers VPC 文档](./docs/connecting-to-private-services.md) | ### 第 7 步. 访问仪表板 `https://.workers.dev/`。创建一个 agent(表单允许 您选择 MicroVM 或 Isolate 后端),启动一个会话,查看 日志。 ### 第 8 步. 保护仪表板 **您的控制平面默认是不安全的!** 一旦您完成了设置,您将需要通过设置 Cloudflare Access 来保护仪表板。 有关更多信息,请参阅 [Cloudflare Access 文档](./docs/securing-access.md)。 ### 第 9 步. 自定义控制平面(可选) Fork 此仓库并对其进行修改以适合您的需求或添加自定义 工具。 ## 深入探索 一旦控制平面启动并运行了第一个端到端的会话, 您可以进一步探索: - [连接到私有服务](./docs/connecting-to-private-services.md) 通过 Workers VPC 绑定在其他云端或本地(甚至在您的笔记本电脑上)进行连接。 - [注入凭证并锁定 agent 会话](./docs/applying-egress-policies.md) 使用出站策略。设置允许/拒绝列表、标头注入、自定义 Worker 代理 以及 VPC 路由。 - [在 Isolate 和基于 VM 的沙箱之间进行选择](./docs/isolate-vs-vm-sandboxes.md) 以获得最佳的 agent 执行环境。 - [设置 Agent 电子邮件](./docs/agent-email.md),为您的新 agent 提供电子邮件地址和发送功能。 - [使用 Browser Run](./docs/browser-rendering-tools.md) 以获得 强大且可观察的 agent 浏览器交互。 - [添加自定义工具](./docs/adding-custom-tools.md) 新工具在一个 文件 [`src/tools/custom-tools.ts`](./src/tools/custom-tools.ts) 中声明。 - [自定义您的沙箱](./docs/customizing-sandboxes.md),通过更改 MicroVM 后端的 `Dockerfile` 和 `instance_type` 设置。 - [了解状态持久化](./docs/snapshots-and-state-persistence.md) 涵盖这两种沙箱类型。 - [探索架构](./docs/architecture.md) 以了解请求生命周期, 从 webhook 入口到分发到任一沙箱后端,并 盘点控制平面使用的每个 Worker 绑定。 - 对新的 CMA 控制平面进行[安全访问](./docs/securing-access.md)。 ## 配置参考 所需的机密和变量: | 名称 | 描述 | |---|---| | `ENVIRONMENT_ID` | 要轮询工作的环境 | | `ANTHROPIC_ENVIRONMENT_KEY` | Anthropic 环境密钥 (sk-ant-oat01-...)。控制平面用于轮询、确认、心跳、强制停止以及会话事件流的单一凭证。在 0.96 SDK / ant 18 CLI 中从 `ANTHROPIC_ENV_KEY` 重命名而来。 | | `ANTHROPIC_API_KEY` | Anthropic API 密钥 (`sk-ant-...`) | | `WEBHOOK_SECRET` | 用于验证 webhook 签名的 HMAC 密钥 | | `CLOUDFLARE_ACCOUNT_ID` | R2 快照(预签名 URL 模式);也由 Browser Rendering REST 工具使用 | | `R2_ACCESS_KEY_ID` / `R2_SECRET_ACCESS_KEY` | R2 快照(预签名 URL 模式) | | `BACKUP_BUCKET_NAME` | R2 快照(预签名 URL 模式) | 运行 MicroVM 沙箱的生产环境部署需要与快照相关的值。 `wrangler dev` 可以通过直接回退到 BACKUP_BUCKET 绑定在没有它们的情况下运行, 但 R2 存储桶本身必须存在(在初始部署中完成)。专门使用 Isolate 沙箱的部署可以完全删除快照机密和 `r2_buckets` 块。 可选的机密: | 名称 | 用于 | |---|---| | `CLOUDFLARE_API_TOKEN` | Browser Rendering REST 工具 | | `ANTHROPIC_BASE_URL` | 覆盖(默认为 `https://api.anthropic.com`) | 可选的变量: | 名称 | 用于 | |---|---| | `EMAIL_DOMAIN` | 每个会话收件箱地址的后缀 | | `EMAIL_FROM` | `cf_email_send` 的默认发件人 | | `EMAIL_FORWARD` | 杂散(非会话)电子邮件的后备收件箱 | 可选的绑定(在 `wrangler.jsonc` 中声明): | 绑定 | 用于 | |---|---| | `BROWSER` | Isolate CDP 浏览器工具 | | `AI` | `cf_image_generate` | | `BACKUP_BUCKET` | 沙箱快照 | | `SEND_EMAIL` | `cf_email_send` | | `vpc_services[]` | 私有 VPC 服务路由 + `cf_call_service` | ## 测试 ``` npm test ``` Vitest 涵盖了出站代理、存储层和 API 表面。VPC 和 Mesh 测试存根已包含但已被注释掉 —— 请参阅 `tests/egress.test.ts` 底部的 `describe.skip(...)` 块以了解计划的形态。 ## 常见陷阱 一些会困扰人们的边缘情况,其中大多数与 `wrangler.jsonc` 中空的 `id` / `database_id` 占位符有关: - **直接运行 `npx wrangler deploy` 会失败。** 提交的 `wrangler.jsonc` 设计上具有空的 KV `id` 和 `database_id` 字段; 如果不先运行修补脚本,wrangler 会拒绝加载它。 使用 `npm run …` 包装器(它会触发 `prebuild`),或者在克隆后运行一次 `npm run prebuild` 以在您的工作树中填充 ID。 `npm run cf-typegen` 也有同样的注意事项 —— 如果它抱怨缺少 ID,请先运行 `prebuild`。 - **不要提交修补后的 ID。** 在本地部署后,脚本会将真实的命名空间/数据库 ID 写入您的工作副本 `wrangler.jsonc` 中。 这些值是特定于账户的。如果您要向规范仓库贡献 PR,请将它们排除在提交之外(使用 `git checkout wrangler.jsonc` 或有选择地暂存)。如果您在个人 fork 上工作,提交它们是没问题的 —— 您的 Workers Builds 重建会对它们执行快速空操作。 - **切换 Cloudflare 账户。** 当本地已经填充了 ID 时,prebuild 快速路径会跳过 API 检查。如果您切换了要部署到的 `CLOUDFLARE_ACCOUNT_ID`,请先运行 `git checkout wrangler.jsonc` 以便将 ID 重置为空,并且脚本会针对新账户重新填充它们。否则,wrangler 将尝试将旧账户的 ID 用于新账户,并因 权限错误而失败。 - **多账户本地开发。** 如果您的 Cloudflare 登录有权访问多个账户,则 prebuild 脚本在非交互模式下无法选择一个。在运行 `npm run deploy` 或 `npm run dev` 之前设置 `CLOUDFLARE_ACCOUNT_ID`(脚本的错误消息列出了候选项)。 - **通过 Deploy to Cloudflare 表单重命名 worker。** 这是安全的 做 —— Cloudflare 的设置页面允许您选择 Worker 名称,以避免与现有的名称发生冲突。KV 命名空间和 D1 数据库 使用新名称作为前缀,因为 ensure 脚本在构建时从 `wrangler.jsonc` 中读取 `name`。 只要记住在第 2 步中配置 Anthropic webhook 时使用重写后的 URL(`https://..workers.dev`)即可。 - **Deploy to Cloudflare 表单:您必须重命名两个 KV 命名空间中的至少一个。** 此仓库声明了两个 KV 命名空间 (`SECRETS` 和 `EGRESS_POLICIES`),并且表单的“Configure resources”步骤用 worker 名称预填充了两个名称输入框,没有绑定后缀 —— 所以第一次创建成功,第二次失败并显示 `Cannot provision a KV Namespace with the title "" because it already exists`。在点击部署之前, 编辑这两个输入框使其不同,例如 `-secrets` 和 `-egress-policies`。 然后 `ensure-kv.mjs` 将在随后的每次构建中模糊匹配这些名称回到正确的绑定。 ## 许可证 [MIT](./LICENSE)
标签:AI智能体, DLL 劫持, MITM代理, 大语言模型, 沙箱管理, 程序员工具, 自动化攻击, 零信任网络, 高对比度