SIwithin Launches: Run Claude Code Unattended in a Sandboxed Budget Fence
Open-source tool SIwithin enables unattended execution of Claude Code or OpenAI Codex within strict file-system fences and dollar budgets. By intercepting API calls via a local proxy to enforce cost caps and generating single audit records per run, it addresses critical safety and budget control issues for autonomous agents.
Full Report
Contents4 sections
SIwithin
SIwithin 以无人值守模式运行 Agent CLI,在指定的文件夹范围内设置隔离围栏,并施加美元预算限制。每次运行结束后,它会留下一条记录。它通过工具机制而非仅凭期望来坚守以下三项承诺:
- 运行仅触及被授权的文件夹。 拒绝访问你的主目录(禁止读写),仅允许访问本次运行指定的文件夹。
- 运行花费不得超过分配的美元预算。 设有单次运行预算、所有运行的总上限以及每次运行的计时器;对于 Claude 适配器,还包含一个回环代理作为通往 API 的唯一入口:运行持有的是单次运行令牌而非你的密钥,无论其如何发起请求,均在此处计量,超出预算即被拒绝。若某 CLI 无法在运行中途停止,除非你明确接受该风险,否则工具将拒绝执行(参见“账本”和“Codex 适配器”章节)。
- 每次运行留下一行记录,说明其成本及是否完成。
支持 Claude Code 和 OpenAI Codex 命令行工具。SIwithin 是一个独立项目,并非由 Anthropic 或 OpenAI 制作、背书或赞助。Claude、Claude Code、OpenAI 和 Codex 均为其各自所有者的名称,此处使用仅为说明 SIwithin 可驱动哪些程序。当你通过 SIwithin 使用这些厂商的 CLI 时,你仍受各厂商服务条款和使用政策的约束;SIwithin 不会改变任何此类条款。
SIwithin 仅支持 macOS。在 Linux 和 Windows 上,它会直接拒绝运行并输出一行提示,而不是在没有隔离围栏的情况下运行。
安装
SIwithin 是单个文件,需要 Python 3.10 或更高版本,仅依赖标准库。它自身不发起任何网络调用,也不发送遥测数据;它为运行启动的代理监听回环端口,且仅与你配置的 API 主机通信。
git clone <this repository> && cd siwithin
python3 siwithin.py --version
# optional: put it on your PATH
install -m 755 siwithin.py ~/.local/bin/siwithin你还需要安装想要驱动的 CLI 并将其加入 PATH,同时为其配置 API 密钥(参见“认证”章节)。
冒烟测试 (python3 tests/smoke.py) 在其编写所用的 Python 3.9.6 上通过。3.10 是支持的最低版本,代码避免了较新的语法特性,但尚未在 3.10 或更高版本上运行过。
快速开始:Claude Code
mkdir -p ~/.config/siwithin && echo 20 > ~/.config/siwithin/cap # all runs together may spend $20
export ANTHROPIC_API_KEY=... # see "Auth"; the tool reads it once, outside the fence, and the run gets a per-run token in its placepython3 siwithin.py --dir ~/work/proj --model sonnet --dry-run < brief.md # 打印所有内容,不执行任何操作
python3 siwithin.py --dir ~/work/proj --model sonnet --budget 2 \
--done "ALL TESTS PASS" --out notes.md < brief.md--dir 指定运行目录:CLI 在该目录中工作并可能向其写入内容(使用 --readonly 可将其设为只读)。--read <folder> 添加允许该运行读取的文件夹。--model 接受模型 ID 或别名(如 haiku、sonnet、opus)。
快速开始:Codex
mkdir -p ~/.config/siwithin && echo 20 > ~/.config/siwithin/cap
export CODEX_API_KEY=...
python3 siwithin.py --adapter codex --model gpt-5.3-codex --soft-budget --network open --dir ~/work/proj --dry-run < brief.md
python3 siwithin.py --adapter codex --model gpt-5.3-codex --soft-budget --network open --budget 2 --dir ~/work/proj < brief.md此适配器需要两个标志,原因详见“Codex 适配器”一节:--model(因为 CLI 仅报告 token 数量而不报告成本,因此需根据模型 ID 计算运行费用)和 --soft-budget(因为 CLI 仅在回合结束时报告使用情况)。该适配器基于文档构建,尚未针对实际运行的 CLI 进行测试。它使用 auth = "env" 模式:密钥位于运行环境的环境中(参见“认证”部分),且由于没有代理服务器,网络防火墙无需开放特定端口,因此必须设置 --network open,或在 config.toml 的 [fence] 部分配置 network = "open";若使用默认设置,运行将被拒绝而非在无网络状态下执行(参见“围栏机制”)。
认证
SIwithin 从不解析、存储、打印或记录密钥,也不会将密钥写入任何文件、日志行或错误消息中。密钥如何传递至 API 取决于适配器的 auth 字段。
Claude 适配器,auth = "proxy"(自 0.3.0 版本起为默认配置)。 在启动前、沙箱隔离区之外,runner 会读取一次密钥:来源可以是其自身环境中的 ANTHROPIC_API_KEY,也可以是 config.toml 中 [auth] key_command 命令输出的第一行内容(该命令由用户定义,用于打印密钥,例如通过钥匙串查询获取)。Runner 保留该密钥,并仅使用标准库在其自身的回环端口上启动一个小型 HTTP 服务器。运行时的环境变量包含 ANTHROPIC_API_KEY=siwithin-<32 个字符>,这是一个每次运行都新生成的令牌,在其他地方毫无价值;以及 ANTHROPIC_BASE_URL=http://127.0.0.1:<port>。运行时发出的每一个请求——无论是通过 CLI、手动发起还是由其启动的第二个 CLI 发出——都会经过这个“门”:代理只接受该运行时的令牌(其他任何令牌均返回 401 且不被处理),仅转发 [auth] paths 中列出的路径(默认为 /v1/messages 和 /v1/messages/count_tokens;其他任何路径均返回 403 且不会附加真实密钥),添加真实密钥,以流式方式中继响应,并根据 [prices] 费率基于用量对每个 /v1/messages 响应进行计价。一旦总费用达到预算上限,后续所有 /v1/messages 请求均返回 402,首次拒绝会像流式停止信号一样终止运行时的进程,且代理将持续拒绝请求直到 runner 退出。当运行时结束时,代理被密封,其日志关闭,服务器停止,因此该令牌变得毫无价值。每个请求会在运行时文件夹中的 proxy.jsonl 里记录一行信息(包括路径、模型、状态码、用量、成本、累计总额、客户端端口、拒绝原因;绝不记录请求体、密钥或令牌)。如果运行时的配置目录中存在一个指定了 apiKeyHelper 的 settings.json,则在启动前会被拒绝,因为 CLI 会在沙箱隔离区内执行该 helper,从而让运行时能够读取它:请将 helper 的命令放入 [auth] key_command 中,这样 runner 会在沙箱隔离区外执行它。--dry-run 会打印 auth: proxy 127.0.0.1:<port> 且不启动任何服务。
auth = "env" 按名称将密钥变量复制到运行时环境中,行为与 0.2.1 版本相同。这是 Codex 适配器的唯一模式,也是 Claude 适配器的可选模式(检查工具会发出警告)。在此模式下,密钥存在于运行时环境中,并被运行时启动的所有命令继承,且无法建立网络防火墙,因为没有可供允许的代理端口:在默认的 [fence] network = "proxy" 设置下,该运行将被拒绝,并且
(注:更多技术实现细节与完整 API 文档请查阅原项目 README)