无论你是重度使用 Codex CLI 的开发者,还是已经把 Claude Code 接进日常提交流程的人,大概率都会遇到同一个体感落差:模型变强了,但“多 Agent 协作”的工程体验并没有跟上。主 Agent 调度 subagent 时,会话上下文变得不可控,工具权限不清晰,日志散落各处,token 消耗也难以核算。
这个项目标题其实已经把范围说得很清楚:Open-sourced runtime for better Codex and Claude subagent experience。它不是又一个 ChatUI 包装,也不负责帮你写 prompt,而是想在 Codex、Claude Code 这样的编程 Agent 与真正执行子任务的 subagent 之间,加一层可插拔、可观测、可控制权限与配额的运行环境。
今天这篇文章会围绕这类 runtime 的价值、架构思路、本地部署方式展开,并用一套通用配置和调用示例,带你把“主 Agent 调 subagent”的真实链路跑通。如果你正在做 AI 编程脚手架、多 Agent 治理,或者只是想知道 Codex / Claude Code 的 subagent 机制到底该怎么在生产环境里收敛,这篇文章可以直接收藏。
1. 核心能力速览
先给一张速览表,帮你快速判断这个方向值不值得投入时间。
| 能力项 | 说明 |
|---|---|
| 项目形态 | 开源 runtime,面向 Codex / Claude Code 的 subagent 调度与运行环境 |
| 解决的核心问题 | subagent 调用链路混乱、权限不清晰、会话上下文互相污染、成本与日志难控制 |
| 主要功能方向 | subagent 注册与调度、工具白名单、会话隔离、请求日志、token 配额、API 网关接入 |
| 硬件门槛 | 与图像 / 视频模型不同,本类项目主要依赖 CPU、内存和网络,不要求独立显卡 |
| 启动方式 | 命令行启动本地服务,再让 Codex / Claude Code 通过工具配置接入 |
| 是否支持 API | 通常可提供 HTTP 接口,方便下游任务批量调用 |
| 是否支持批量任务 | 可以,但需要自行设计队列、重试与幂等机制 |
| 是否支持本地模型 | 取决于后端接入方式,runtime 本身更接近模型无关的调度层 |
| 适合场景 | 多仓库维护、PR 自动审查、批量测试修复、代理工具链治理、企业级 AI 编程基础设施 |
| 不适合场景 | 只希望一键让 Codex 变强、没有 subagent 编排诉求、不愿维护额外服务的场景 |
说明:因为该项目的仓库 README、具体命令和接口定义尚未在此处给出,下面的部署和调用示例统一采用通用模板。实际操作时,请把路径、端口、模型名和接口路径替换成你自己项目 README 里的真实值。
2. 为什么 Codex 和 Claude 需要单独的 subagent runtime
2.1 subagent 在主从模式里到底承担什么
最新的多 Agent 设计里,一种非常主流的方式是主从模式:主 Agent 负责理解任务、拆解步骤、规划工具调用,subagent 负责执行局部的、有边界的子任务。从实现角度看,主 Agent 本质上会把 subagent 当成另一种“tool”来调用,只是这个 tool 的能力更复杂,背后可能挂着一整套独立的提示词、上下文记忆和工具链。
这是一种非常务实的设计。相比让一个超长上下文的 Agent 处理所有事情,把子任务拆给专用 subagent,可以避免“什么都会,什么都不精”的问题。例如:
- 代码审查就交给 code-reviewer subagent;
- 测试生成就交给 test-writer subagent;
- 文档修复就交给 doc-fixer subagent;
- 依赖升级影响分析就交给 dependency-auditor subagent。
2.2 原生 Agent 调用链的三个痛点
直接用 Codex CLI 或 Claude Code 跑简单任务时,体验通常不错。但一旦 subagent 开始被频繁调用,下面三个问题会迅速暴露。
第一个问题是上下文隔离不足。主 Agent 和 subagent 往往共享同一个父任务上下文,子任务产生的中间输出很容易倒灌到主上下文里。任务一多,模型注意力被无关信息冲散,回答质量会明显下降,token 消耗也会快速上升。
第二个问题是权限边界粗糙。主 Agent 能访问工具,那 subagent 是否也应该拥有同样的工具权限?如果 subagent 能自由读写文件、执行 shell 命令、调用网络接口,那任何一个子任务里出现 prompt 注入或误判,都可能造成超出预期的副作用。原生工具往往很难按 subagent 维度做细粒度权限隔离。
第三个问题是可观测性和成本核算缺失。每次 subagent 调用消耗了多少 token、调用了哪几个工具、成功还是失败、失败原因是什么,如果这些信息散落在终端输出里,没有结构化日志,团队就很难对 Agent 行为做审计,也很难判断一次重构到底值不值得交给 Agent 完成。
2.3 runtime 要解决的本质问题
所以这里需要的不是一个新的模型,而是一个 runtime。
它做的事本质上和传统的应用运行时一样:把进程放到可控环境里,提供生命周期管理、资源限制、权限控制和观测能力。只不过这次被管理的对象变成了 AI Agent。
一个设计良好的 subagent runtime 至少要做这几件事:
- 会话隔离:每个 subagent 拥有独立上下文空间,只接收主 Agent 传递的最小任务描述;
- 注册与发现:让主 Agent 知道存在哪些 subagent,以及每个 subagent 的输入输出格式;
- 权限代管:在 runtime 层统一做工具白名单、目录白名单、网络权限与命令执行策略;
- 配额控制:对 token、请求次数、单任务运行时长做限制;
- 结构化日志:记录每次 subagent 调用的输入、输出、耗时、成本与错误;
- 模型无关:同一套 runtime 可以对接 Codex、Claude Code,也可以对接本地模型或私有化模型端点。
总的来说,runtime 就是把原本写死在 Agent 内部的工具调用规则,抽到一个我们能审计、能配置、能热更新的独立服务里。
3. 适用场景与合规边界
3.1 什么场景值得用
如果你符合下面任意一条,这个方向值得认真测试:
- 团队里已经有多名成员在使用 Codex CLI 或 Claude Code,希望统一工具策略;
- 你同时接入了多个模型服务,希望切换模型时不用重写 subagent 编排逻辑;
- 你需要在 CI/CD 流水线里跑批量代码审查、批量补测试、批量升级依赖;
- 你有权限审计和成本分摊的硬需求,不能让每个 Agent 都裸奔着访问公司仓库;
- 你要把 Codex / Claude Code 接到内部知识库、内部 API 上,不想把工具密钥散落到每个人终端里。
反过来,如果只是个人开发者做一次性脚本、写小工具,或者只是想“让 Codex 更听话”,那么上一套 runtime 反而增加维护负担。先用好原生的 subagent 机制即可。
3.2 安全、授权与合规边界
由于 runtime 会承接真实代码仓库的操作能力,风险等级比普通 AI 聊天工具高很多。使用前必须明确下面几条边界:
- 对仓库的写操作、shell 命令执行、外部 API 调用,默认都应设置为“允许列表”之外的禁止项;
- 涉及人脸、声音、私人数据或企业未公开数据时,先确认是否有合法授权,不要在未授权数据集上做自动处理;
- API Key、访问令牌、内部域名等敏感信息不能写死在代码仓库、配置文件和日志里,建议通过环境变量或密钥管理服务注入;
- subagent 自动生成的代码、自动修改的文件,上线前必须经过人工 review;
- 接入第三方模型平台时,要遵守对应服务的使用条款和企业内部数据合规要求。
4. 环境准备与依赖检查
4.1 推荐环境
这种运行时服务通常部署在开发机或轻量服务器上,不涉及 GPU 显存,但对内存和并发能力有要求。推荐环境如下:
| 依赖项 | 建议要求 |
|---|---|
| 操作系统 | Linux / macOS 优先;Windows 可通过 WSL 运行,具体看项目官方支持情况 |
| 包管理器 | Python 3.11+ 的 pip / venv,或 Node.js 18+ 的 npm / pnpm,取决于项目实现 |
| 终端 Agent | Codex CLI 与 Claude Code 应已能独立运行 |
| 网络 | 能访问模型服务 API,企业网络需确认 Endpoint 白名单 |
| 磁盘 | 预留 5GB 以上空间,日志和会话数据会持续增长 |
4.2 版本自检命令
部署之前,先确认本机基础环境可用:
codex --version claude --version python3 --version node --version git --version如果你连 Codex 或 Claude Code 都无法在终端正常启动,那后续 runtime 接入很难顺畅。例如 Windows PowerShell 里经常出现claude 无法识别为 cmdlet的报错,本质是安装后没有把可执行文件加入 PATH,或者安装脚本没有执行成功。解决这类基础问题之前,先不要引入 runtime 层。
4.3 端口与目录规划
本地调试时建议固定一个端口,例如 8231,并把日志写到单独目录。开始前检查端口是否被占用:
lsof -i :8231如果输出为空,说明端口可用。如果被占用,就换一个端口,runtime 服务、Codex 和 Claude Code 的配置要同步更新。
5. 安装部署与启动方式
下面给出一套通用部署流程。真实项目可能采用 Python 或 Node.js 实现,这里以 Python 虚拟环境为例,操作时替换成你自己的地址和模块名。
5.1 克隆项目并安装依赖
git clone https://github.com/your-name/agent-runtime.git cd agent-runtime # 创建并激活虚拟环境 python3 -m venv .venv source .venv/bin/activate # 安装依赖 pip install -r requirements.txt如果项目采用 Node.js 实现,则对应为:
npm install如果安装依赖时出现网络超时或缺少编译工具,先检查 npm / pip 镜像源配置,再检查系统是否缺少 Python 头文件或 C++ 构建链。
5.2 配置环境变量
runtime 本身不承担模型推理,但要让 Codex 或 Claude Code 正常回传结果,就需要正确注入对应平台的访问凭证。配置示例:
export OPENAI_API_KEY="sk-xxxx" export ANTHROPIC_API_KEY="sk-ant-xxxx" # 如果使用本地或第三方自定义模型端点 export CODEX_ENDPOINT="http://127.0.0.1:8000/v1" export CLAUDE_ENDPOINT="http://127.0.0.1:8000/v1"注意,不同版本对 Endpoint 和模型名格式的要求不一样。真实环境里,建议把这些密钥放到.env文件而不是终端历史记录中。.gitignore里必须排除.env,避免误提交。
5.3 启动 runtime 服务
通用启动命令如下:
python run_server.py --host 127.0.0.1 --port 8231启动后观察日志,确认端口监听成功。如果项目自带 WebUI 或控制台面板,打开http://127.0.0.1:8231应该能看到服务状态页。没有页面时,直接请求健康检查接口即可。
5.4 让 Codex / Claude Code 接入 runtime
接入方式通常有两种:一种是把 runtime 暴露为工具服务器,让 Codex / Claude Code 在运行过程中调用;另一种是使用官方支持的 subagent 配置,把 runtime 的地址写进配置文件。
以 Claude Code 为例,工具服务器配置通常会写在~/.claude/settings.json中。通用示例:
{ "tools": { "agent-runtime": { "command": "python", "args": ["runtime_client.py", "--server", "http://127.0.0.1:8231"], "env": {}, "timeout": 300 } } }以 Codex 为例,如果你使用的是 YAML 配置文件,可以尝试声明一个本地 endpoint 或自定义工具源。需要注意:不同 Codex 版本对配置字段名区分很严格,如果报model not supported,大概率是写入的模型 ID 不在当前版本识别范围内,需要去查官方支持的模型列表。
5.5 验证服务连通
启动 runtime 后,先用 curl 做一次连通性检查:
curl http://127.0.0.1:8231/health预期返回类似{"status":"ok"}的 JSON。如果请求超时,按下文第 9 节排查端口、防火墙与进程日志。
6. 功能测试与效果验证
6.1 验证 subagent 能否被拉起
连接 runtime 后,第一个测试不是让它写真实代码,而是验证“主 Agent 能正确发现并拉起一个 subagent”。
测试输入:让 Claude Code 执行一条非常简单的子任务,例如:
调用 code-reviewer subagent,检查当前目录下 README.md 是否存在明显格式问题。判断标准:
- 主 Agent 正确调用了 runtime 提供的 code-reviewer 服务;
- subagent 正常返回结构化结果;
- 主 Agent 能基于返回结果给出最终总结。
如果这里失败,不要急着调整模型 prompt,先看 runtime 日志里有没有注册表加载记录,再看 Codex / Claude Code 是否真的加载了新工具配置。很多时候问题出在配置文件没被重新加载,需要重启终端或 Agent 进程。
6.2 验证单次 subagent API 调用
命令行交互不容易沉淀成自动化用例,所以第二步是直接调用 runtime 的 HTTP 接口。以下代码只是演示 subagent 调度层常见的请求结构,实际字段名需要以项目接口文档为准:
import requests BASE_URL = "http://127.0.0.1:8231" payload = { "agent": "code-reviewer", "task": "review current git diff and list potential bugs", "permissions": { "read": ["repo"], "write": [] }, "max_steps": 20, "timeout_seconds": 120 } resp = requests.post(f"{BASE_URL}/v1/subagent/run", json=payload, timeout=180) print(resp.status_code) print(resp.json())成功时,返回结果应包含:
output:subagent 生成的结论;usage:token 消耗;duration_ms:耗时;status:completed/failed等状态字段。
如果返回 404,去项目文档里确认路由前缀是/v1还是其他路径。如果返回 401,则检查服务启动时是否开启了鉴权,以及请求里是否带上了对应令牌。
6.3 验证 Codex 批量审查同一条 diff
当单次调用成功后,再回到 Codex CLI 做端到端验证。测试目的不是让 subagent 产出惊艳方案,而是验证工程链路稳定:
# 在目标代码仓库内执行 codex exec "use runtime code-reviewer agent to review last commit"观察三个指标:
- 请求是否在合理时间内返回;
- 返回结果是否以结构化 JSON 写入了 runtime 日志;
- 整个过程中,是否出现了超出配置权限的文件写入或命令执行记录。
如果一切正常,说明 runtime 已经能对 Codex 的 subagent 调用做代理和观测。之后再逐步放开权限,去测试 Claude Code 的同类能力。
6.4 常见失败判断清单
| 测试现象 | 判断方向 |
|---|---|
| subagent 没被拉起 | runtime 服务状态、工具配置加载、Agent 进程是否重启 |
| subagent 被拉起但报权限错误 | 检查 runtime 配置里的工具白名单和目录白名单 |
| 输出质量明显低于原生模式 | 检查是否把过多上下文塞进子任务、子任务提示词是否清晰 |
| 接口调用超时 | 检查单任务超时时间、subagent 循环是否失控、模型服务是否过载 |
7. 接口 API 与批量任务设计
7.1 runtime 作为 API 网关
runtime 一旦以 HTTP 服务形式存在,就可以作为 API 网关接入 CI/CD 流水线。常见的接口层能力包括:
- 注册一个新的 subagent;
- 查询当前可用的 subagent 列表;
- 提交一个 subagent 执行任务;
- 获取任务状态与结构化日志;
- 取消一个卡住的 subagent 任务。
注册 subagent 的通用请求示例:
{ "name": "dependency-auditor", "description": "分析项目依赖升级影响范围,输出风险清单", "model": "default", "permissions": { "read": ["repo", "lockfile"], "write": [] }, "max_steps": 30 }7.2 批量任务设计
真实场景里,你往往需要让同一个 subagent 处理多个仓库或多次提交。此时不要直接开一堆终端并发跑,而是建议做一个简单的任务队列。
批量任务配置文件:
{ "queue": [ { "task_id": "repo-a-review", "agent": "code-reviewer", "repo": "/workspaces/repo-a", "target": "HEAD~3..HEAD" }, { "task_id": "repo-b-review", "agent": "code-reviewer", "repo": "/workspaces/repo-b", "target": "HEAD~1..HEAD" } ], "concurrency": 2, "failure_policy": "retry_once" }批量提交脚本示例:
import json import time import requests config = json.load(open("batch_tasks.json")) BASE_URL = "http://127.0.0.1:8231" results = [] for task in config["queue"]: resp = requests.post( f"{BASE_URL}/v1/subagent/run", json=task, timeout=300, ) data = resp.json() results.append({ "task_id": task["task_id"], "status": data.get("status"), "duration_ms": data.get("duration_ms"), "succeeded": data.get("status") == "completed", }) time.sleep(1) # 防止请求过快 for item in results: print(item)批量任务比单任务更需要关注三点:
- 幂等性:同一个任务重试不能重复提交改动或重复写文件;
- 资源上限:并发数要限制,不然模型 API 限流和内存占用会同时报警;
- 失败重试策略:建议只对网络超时、临时 5xx 错误自动重试,对 Agent 判定为“任务无法完成”的情况不要无脑重试。
7.3 API 鉴权建议
如果 runtime 监听地址不是127.0.0.1,而是开放到局域网或服务器公网,必须启用鉴权。最简单的方式是增加一个Authorization: Bearer <token>请求头,并由服务端校验 token。不要裸奔暴露接口,否则任何能访问端口的人都能调用你的 Codex / Claude Code 凭证去消耗模型额度。
8. 资源占用与性能观察
8.1 runtime 本身不烧显存
再次强调,这个 runtime 和图像生成、视频生成项目不同,它在资源占用上主要关注的是 CPU、内存和文件句柄。真正的大头通常来自两个地方:
- Codex CLI 和 Claude Code 各自维护的会话进程;
- 引入本地模型或私有化模型时,模型服务自身的占用。
如果你只是把 runtime 接 OpenAI / Anthropic 官方 API,那么本机资源压力一般不大。可以通过top或ps观察:
ps aux --sort=-%mem | grep -E "codex|claude|runtime_server" | head -20如果你在 runtime 后面接了本地模型做测试,那就需要额外观察显存:
nvidia-smi注意,这属于模型服务侧的资源占用,不能计算到 runtime 头上。
8.2 影响性能的关键变量
让 subagent 运行变慢的常见原因如下:
- 历史上下文过长:即使做了会话隔离,单次 subagent 任务如果传入了过多文件内容,模型首字延迟仍会上升;
- 并发 subagent 数量过高:同时拉起太多子任务,会让日志、工具调用和模型 API 请求互相争抢;
- 工具调用链路过长:subagent 每次调用外部工具都有往返延迟,工具越多,任务耗时越长;
- max_steps 设置过大:Agent 在复杂问题上可能进入低效循环,重复读取同一个文件、反复执行类似命令。
8.3 降低资源消耗的建议
- 给每个 subagent 设置合理的
max_steps,不要默认给 100; - 按任务类型拆分输入,不要把整个 monorepo 全塞给 subagent;
- 用临时目录承载 subagent 的写操作,任务结束后清理;
- 开启压缩日志或日志轮转,避免
.log文件无限增长。
9. 常见问题与排查方法
这里把 Codex / Claude Code 接入 runtime 时最容易遇到的几类问题整理成表,方便直接对照排查。
| 问题现象 | 可能原因 | 排查方式 | 解决方案 |
|---|---|---|---|
| Cli 提示“无法将 claude 项识别为 cmdlet” | Claude Code 未安装或未加入 PATH | 重新执行安装脚本,检查安装路径 | 退出终端重新打开,或手动把可执行目录加入 PATH |
| Electron 桌面版报 “could not find the WebView2 Runtime” | 系统缺少 Edge WebView2 运行库 | 检查系统组件安装状态 | 安装对应平台的 WebView2 Runtime 后重启应用 |
| 提示 “unable to locate the codex cli binary” | Codex CLI 路径未被桌面应用识别 | 在应用设置里查看 CLI 路径,确认codex命令是否可用 | 显示设置 Codex CLI 路径,或重装 Codex CLI |
| 使用自定义模型源时提示 model not supported | 当前 Codex 版本不支持写入的模型 ID | 查看 Codex CLI 文档或源码中的模型清单 | 更换为支持的模型 ID,或升级 Codex CLI 版本 |
| Runtime 启动后端口被占用 | 端口冲突 | lsof -i :8231查看占用进程 | 换端口启动,并同步修改 Codex / Claude Code 配置 |
| HTTP 请求返回 401 | 鉴权 token 未传或不对 | 检查启动参数中是否开启鉴权 | 在请求头加入正确的Authorization: Bearer token |
| Subagent 能拉起但总是权限拒绝 | runtime 工具白名单或目录白名单过严 | 查看 runtime 日志中具体是哪一次权限校验失败 | 调整配置,放开必要路径,保持最小权限原则 |
| 批量任务跑到一半卡住 | subagent 进入循环或模型 API 超时 | 查看任务队列状态和 runtime 日志 | 设置单任务超时时间,增加失败重试或直接终止任务 |
| 输出结果不稳定,同样任务每次结果不同 | 模型采样随机性导致 | 在配置中打开 temperature 控制参数 | 对需要稳定输出的审计任务使用较低 temperature |
这些排查经验不一定完全对应你下载的 runtime 实现,但总体上是一致的:先定位是 CLI 问题、runtime 问题还是模型服务问题,不要一上来就怀疑核心逻辑。
10. 最佳实践与落地建议
10.1 用最小复现做基线
第一次接入不要直接跑全量仓库。我的建议是创建一个临时目录,里面放两个小文件,然后让 subagent 执行一项确定性很强的任务,比如“找出第二个文件里的语法错误”。以这种最小复现验证“主 Agent -> runtime -> subagent -> 返回结果”链路能走通,再逐步扩大范围。
10.2 沉淀一套可复用配置
最少要维护两个层面的配置:
- runtime 基础配置:监听端口、模型默认列表、默认权限、默认超时;
- subagent 模板配置:每个 subagent 自己的提示词边界、输入输出格式、可读目录、可执行命令白名单。
配置示例:
runtime: host: 127.0.0.1 port: 8231 auth_token_env: RUNTIME_TOKEN subagents: code-reviewer: description: "审查代码 diff,输出 bug 风险列表" read_paths: - "." write_paths: [] allowed_commands: [] max_steps: 20 timeout_seconds: 120 test-writer: description: "为指定函数生成单元测试" read_paths: - "src" - "tests" write_paths: - "tests" allowed_commands: [] max_steps: 30 timeout_seconds: 180这份配置体现的核心思想是:每个 subagent 都不是全能的,它的权限范围越小,越容易控制风险。
10.3 把日志纳入审计体系
runtime 最有价值的产品点之一就是结构化日志。建议至少记录这几个字段:
- subagent 名称和版本;
- 输入的任务描述;
- 实际调用的工具列表;
- 每个工具的输入摘要与输出摘要;
- token 消耗与耗时;
- 最终状态与失败原因。
如果团队已经有日志平台,就把 runtime 的日志转发过去。日后如果出现 Agent 做了危险操作,你能在几分钟内回答“是哪个子任务、哪一次工具调用、由谁发起”的。
10.4 给 Agent 循环兜底
在没有任何权限控制的条件下,把 Codex / Claude Code 接进自动流水线是危险的。建议做到:
- 写操作必须在独立分支或临时目录进行;
- 涉及
git push、git merge、rm等高风险命令默认拒绝; - 单次任务设置硬超时,超时后直接终止,不给 Agent 无限重试的机会;
- 关键流程保留人工确认环节,例如 merge request 必须有人 review。
11. 更适合进一步实践的路径
如果你已经把 Codex CLI 或 Claude Code 用在日常开发里,那么下一步建议很直接:拉开一个最小仓库,配置一个只读权限的 code-reviewer subagent,先跑三天看看。重点观察 runtime 是否真的让你对每次调用有了清晰感知,而不只是把 Agent 调用从终端搬到了另一个工具里。
这个方向最值得尝试的点,是把原来零散分布在各种终端文本里的 subagent 调用,变成一个带权限、带日志、带配额的工程链路。最容易踩的坑往往也不是模型能力不够,而是历史上下文没隔离、写权限给得过大、以及没有设置超时与重试策略。
如果后续这个 runtime 能支持更多 Agent 类型,并且接口稳定下来,它完全有潜力成为团队内统一接入 AI 编程能力的基座。当前阶段,建议你先从“最小可运行配置加只读权限”开始,用真实任务验证它是否值得长期维护下去。