Anthropic 的 Claude Agent 能做复杂推理和多步骤任务,但真正把它放进生产环境,开发者要面对一堆琐碎问题:Agent 怎么安全地访问内网数据库?跑在哪个 runtime?执行日志怎么追踪?Cloudflare 最近上线了对 Claude Managed Agents 的支持,把这几件事打包到了同一套基础设施里——Workers 的边缘 runtime、Tunnel 的私有网络穿透、Logpush 的日志管道,全部可以直接对接 Agent 的生命周期。
Agent 不只是"调一次 API"
普通 LLM 调用是单轮请求-响应;Agent 则是自主规划、多步执行、中途可能调用外部工具。这意味着两件事:
- Agent 需要长时间运行且可能重试——runtime 要能撑住几十秒甚至几分钟的执行,不能像普通 HTTP 请求那样 10 秒超时就断。
- Agent 要访问你的私有资源——数据库、内部 API、消息队列,这些不该暴露到公网。
Cloudflare 的方案用 Workers 作为 Agent runtime,用 Tunnel 打通私有系统,用 Logpush / Workers Analytics 把执行过程变成可查询的结构化数据。开发者不用自己拼这套管道。
连接私有系统:Tunnel + Agent 的组合
传统做法是把内部服务开一个公网端口,再加 IP 白名单——风险高、维护成本大。Cloudflare Tunnel 的思路是反过来的:从内网主动建一条加密隧道到 Cloudflare 边缘,外部请求通过 Cloudflare 网关进入隧道,内网服务本身零暴露。
Agent 场景下,Tunnel 的价值更明显:Agent 在 Workers 上跑,需要调用内网的 PostgreSQL 或 Redis,直接走 Tunnel 路由,不需要任何公网入口。下面是一个最小化的 Tunnel + Agent 配置示例。
# cloudflare-tunnel-config.yml
tunnel: my-agent-tunnel
credentials-file: /etc/cloudflare/.tunnel-credentials.json
ingress:
# Agent 调用内部用户查询 API
- hostname: agent-internal-api.my-domain.com
service: http://user-service:8080
# Agent 读取内部 PostgreSQL(通过 PostgREST 暴露)
- hostname: agent-db.my-domain.com
service: http://postgrest:3000
# 兜底规则
- service: http_status:404
启动 Tunnel:
# 安装 cloudflared 后,创建并运行隧道
cloudflared tunnel create my-agent-tunnel
cloudflared tunnel route dns my-agent-tunnel agent-internal-api.my-domain.com
cloudflared tunnel route dns my-agent-tunnel agent-db.my-domain.com
cloudflared tunnel --config cloudflare-tunnel-config.yml run my-agent-tunnel
这样 Agent 在 Workers 里发请求到 https://agent-internal-api.my-domain.com,流量会经 Cloudflare 边缘进入 Tunnel,直达内网服务,全程 TLS 加密、零公网暴露。
在 Workers 上跑 Agent:一个可改造的完整示例
下面是一个在 Cloudflare Workers 中集成 Claude Agent 的最小项目。它演示了:初始化 Agent、让它调用内部 API(走 Tunnel)、返回结构化结果。你可以直接复制改造。
# 初始化 Workers 项目
npm create cloudflare@latest -- my-claude-agent
cd my-claude-agent
// src/index.ts — Cloudflare Worker 入口
interface Env {
ANTHROPIC_API_KEY: string;
INTERNAL_API_URL: string; // Tunnel 地址,如 https://agent-internal-api.my-domain.com
}
export default {
async fetch(request: Request, env: Env): Promise<Response> {
// 1. 从请求中获取用户指令
const { task } = await request.json() as { task: string };
// 2. 定义 Agent 可用的工具
const tools = [
{
name: "query_user_profile",
description: "通过用户 ID 查询内部用户档案",
input_schema: {
type: "object",
properties: {
user_id: { type: "string", description: "内部用户 ID" },
},
required: ["user_id"],
},
},
];
// 3. 调用 Claude Agent API(使用 tool_use 模式)
const agentResponse = await fetch("https://api.anthropic.com/v1/messages", {
method: "POST",
headers: {
"x-api-key": env.ANTHROPIC_API_KEY,
"anthropic-version": "2023-06-01",
"content-type": "application/json",
},
body: JSON.stringify({
model: "claude-sonnet-4-20250514",
max_tokens: 4096,
system: "你是一个内部运营助手。收到任务后,按步骤调用工具完成,最后给出结构化总结。",
messages: [{ role: "user", content: task }],
tools,
}),
});
const agentResult = await agentResponse.json() as any;
// 4. 如果 Agent 请求调用工具,执行工具调用并继续对话
if (agentResult.stop_reason === "tool_use") {
const toolCall = agentResult.content.find((block: any) => block.type === "tool_use");
const toolInput = toolCall.input as { user_id: string };
// 调用内部 API(走 Cloudflare Tunnel)
const internalRes = await fetch(`${env.INTERNAL_API_URL}/users/${toolInput.user_id}`, {
headers: { "Authorization": "Bearer internal-token" },
});
const userProfile = await internalRes.json();
// 把工具结果喂回 Claude,让它继续推理
const followUp = await fetch("https://api.anthropic.com/v1/messages", {
method: "POST",
headers: {
"x-api-key": env.ANTHROPIC_API_KEY,
"anthropic-version": "2023-06-01",
"content-type": "application/json",
},
body: JSON.stringify({
model: "claude-sonnet-4-20250514",
max_tokens: 4096,
system: "你是一个内部运营助手。收到任务后,按步骤调用工具完成,最后给出结构化总结。",
messages: [
{ role: "user", content: task },
{ role: "assistant", content: agentResult.content },
{
role: "user",
content: [
{
type: "tool_result",
tool_use_id: toolCall.id,
content: JSON.stringify(userProfile),
},
],
},
],
tools,
}),
});
const finalResult = await followUp.json() as any;
return Response.json(finalResult);
}
// 5. Agent 直接给出文本回复
return Response.json(agentResult);
},
};
# wrangler.toml — Workers 部署配置
name = "my-claude-agent"
main = "src/index.ts"
compatibility_date = "2025-06-18"
[vars]
INTERNAL_API_URL = "https://agent-internal-api.my-domain.com"
# API Key 用 secret 管理,不要硬编码
# 运行: wrangler secret put ANTHROPIC_API_KEY
部署:
wrangler secret put ANTHROPIC_API_KEY # 输入你的 Anthropic API Key
wrangler deploy
部署后用 curl 测试:
curl -X POST https://my-claude-agent.my-domain.com \
-H "content-type: application/json" \
-d '{"task": "查询用户 u-12345 的档案,判断是否满足升级条件"}'
Agent 会先调用 query_user_profile 工具,Worker 通过 Tunnel 拿到内网数据,再把结果喂回 Claude 做判断——整个过程在边缘 runtime 完成,内网服务不暴露。
可观测:知道 Agent 到底干了什么
Agent 的黑盒问题是生产环境最大的痛点。Cloudflare 的方案是让 Agent 的每一步执行都通过 Workers Analytics 和 Logpush 落地:
- Workers Analytics:记录每次 Agent 请求的耗时、token 消耗、工具调用次数,可以在 Cloudflare Dashboard 直接看趋势图。
- Logpush:把结构化日志推到你的 R2 存储、S3 或外部分析平台(如 Datadog),做更细的审计。
启用 Logpush 到 R2 的配置:
# 创建 R2 Bucket 接收日志
wrangler r2 bucket create agent-logs
# 启用 Logpush,把 Workers 日志推到 R2
curl -X POST "https://api.cloudflare.com/client/v4/zones/{zone_id}/logpush/jobs" \
-H "Authorization: Bearer {cf_api_token}" \
-H "content-type: application/json" \
-d '{
"name": "agent-activity-logs",
"logpull_options": "fields=Event,EventTimestamp,Outcome,RequestPath,ResponseStatus,OriginIP×tamps=rfc3339",
"destination_conf": "r2://agent-logs/{zone_id}/{date}",
"filter": "{\"where\": {\"key\": \"RequestPath\", \"operator\": \"startsWith\", \"value\": \"/my-claude-agent\"}}"
}'
这样每次 Agent 调用内部 API、每次工具执行的结果,都会以 JSON 形式存进 R2,你可以用 Athena 或 DuckDB 做事后查询:
-- 用 DuckDB 查询最近 7 天 Agent 调用内部 API 的失败率
SELECT
date,
count(*) AS total_calls,
count_if(ResponseStatus >= 400) AS failures,
round(failures / total_calls * 100, 2) AS failure_pct
FROM read_json_auto('r2://agent-logs/*/*.json')
WHERE EventTimestamp >= current_timestamp - interval '7' day
GROUP BY date
ORDER BY date;
上线前的检查清单
把 Claude Agent 跑在 Cloudflare 上确实省了不少基础设施工作,但上线前有几件事必须确认:
| 检查项 | 说明 |
|---|---|
| API Key 安全 | 用 wrangler secret 管理,绝不硬编码到代码或环境变量文件 |
| Tunnel 认证 | 内网服务即使走 Tunnel,也应校验请求来源(如 Service Token),防止同一 Tunnel 上的其他路径被滥用 |
| 执行超时 | Workers 有 CPU 时间限制(免费版 10ms,付费版 30s),Agent 多步推理可能超限——考虑用 Durable Objects 延长执行窗口 |
| Token 成本 | Agent 多轮推理的 token 消耗远高于单次调用,务必在 Analytics 里监控 max_tokens 实际使用量,设上限 |
| 日志脱敏 | Agent 工具结果可能包含用户隐私数据,Logpush 到外部存储前做字段过滤或脱敏 |
| 回退策略 | Agent 调用失败时(内部 API 挂了、Claude 超时),Worker 应返回明确错误码,不要静默吞掉 |
Cloudflare 把 runtime、网络穿透、可观测三件事串起来,确实让 Agent 从"能跑 demo"到"能上生产"的距离缩短了不少。但 Agent 的不确定性本身不会因为基础设施变好而消失——监控、限流、回退策略,这些仍然是开发者自己要守的底线。