持久化工具容器执行服务

PTC MCP是一个为Claude Code提供沙盒化Python执行环境的Docker容器服务,具有持久化状态和可组合的分析库,适用于代码库映射、论文研究和网页提取。

  • by KartikKatam
  • Python
  • 本地部署
  • 更新于
在 GitHub 查看 KartikKatam/ptc-mcp-server

使用说明

PTC MCP——持久性工具容器

一个MCP服务器,为Claude Code在Docker容器中的沙盒Python执行提供持久状态,以及一个用于代码库映射、论文研究和web提取的可组合分析库。

作为一个研究项目来回答: 给人工智能代理更好的工具真的能节省代币并提高输出质量吗?

事实证明,答案比预期的更加微妙。


问题

Claude Code代理在探索代码库时会进行许多连续的工具调用——Glob、Read、Grep、Read、Read、Grep——每个调用都会将文件内容添加到上下文中。一次典型的探索需要10-15次工具调用和8-15K个上下文令牌,其中大部分是代理读取一次并汇总的原始文件内容。

假设:进行探索 在沙箱里,只返回摘要。一次往返,而不是十次。上下文减少95%。

建筑

Claude Code session
    │
    ├── ptc_execute(code)          ← single MCP tool call
    │       │
    │       ▼
    │   PTC Server (SSE, port 8741)
    │       │
    │       ▼
    │   Container Manager
    │       ├── Docker container pool (persistent, session-scoped)
    │       ├── Unix socket IPC (host ↔ container)
    │       └── REPL processes (persistent namespace per agent)
    │               │
    │               ▼
    │           ptc_tools library
    │               ├── repomap     (tree-sitter + PageRank)
    │               ├── symbols     (AST extraction, API diffing)
    │               ├── dependencies (call graphs, import cycles, change impact)
    │               ├── contracts   (env deps, shared state, side effects)
    │               └── research    (web search, papers, PDF, fetch pipelines)
    │
    └── result (stdout only)       ← summary returns to context

关键基础设施决策:

  • 持久容器 使用会话范围的生命周期——变量在调用中存活,首次使用后不会冷启动
  • Unix套接字IPC 代替docker exec——低延迟、结构化协议
  • 看门狗守护进程 通过崩溃恢复,服务器重新启动并重新连接到幸存的容器
  • 命名空间丢失检测 --如果集装箱被收割,状态消失,代理将收到警告

评价

方法论

100个Sonnet代理在5个领域的25个分析任务中进行调度:

域 任务 示例
API表面分析 5 “记录pydantic's validation API”
代码库分析 6 “绘制这个2894文件Django项目的路由架构”
影响分析 4 “如果我重命名架构/目录,会有什么问题?”
论文研究 5 “调查2023年以来变压器效率的提高”
网络研究 5 “比较FastAPI与Django与Flask的性能”

每个任务由3个代理配置运行:

  • 香草 --仅限Claude的原生工具(Read、Grep、Glob、WebSearch)
  • 工具 --带原始工具库(build_graph、paper_search等)的PTC沙盒
  • 食谱 --PTC沙箱,具有两个步骤发现然后提取模式

所有75项输出均由25名独立的法学硕士评委进行评估,评分正确性、完整性、准确性、可操作性和深度(每人1-10分)。

完整评估数据: ptc_tools/benchmarks/results/

结果

质量

代理 正确性 完整性 精确性 可操作性 深度 胜利
工具 8.9 8.4 7.8 8.3 8.0 7
食谱 8.4 7.9 7.9 7.8 7.4 11
香草 8.1 7.9 6.9 7.5 7.8 7

令牌效率(令人不舒服的发现)

代理 平均代币 得分/1K代币 每赢代币
香草 5,374 1.42 19,193
食谱 9164 0.86 20827
工具 9580 0.87 34214

Vanilla的代币效率是PTC工具的1.6倍。 它的得分为93%,成本为56%。

PTC的最坏情况:

  • WR-2(异步最佳实践):vanilla在2.3K代币中得分为9.4;工具在18.9万个代币中得分9.2-- 更糟糕的答案需要8倍的成本
  • WR-3(WASM运行时):得分相同,工具成本增加2.7倍
  • AP-5(pathlib):香草在质量和成本上都赢了

工具” 存在 改变了代理行为。当工具可用时,即使代理人已经知道答案,他们也会进行更多的探索。

关键发现:路由,而非工具

没有一种方法占主导地位。任务形状决定了最佳策略:

Task arrives
    │
    ├── Model already knows the answer?        → VANILLA  (save 1.7x tokens)
    │   (well-documented APIs, stable patterns)
    │
    ├── Need precise targeted facts?           → TOOLS    (highest avg scores)
    │   (find callers, fetch benchmarks)
    │
    ├── Large search space, selection matters?  → RECIPES  (most 1st-place wins)
    │   (survey papers, navigate large codebases)
    │
    └── Uncertain?                             → TOOLS    (safest default)

正确调度的路由策略获胜 25/25任务任何一种方法最多只能获胜11次。

PTC真正增值之处

这些工具并非普遍更好,但它们为特定的任务形状提供了更好的工具 模型实际上无法访问的功能:

任务形状 为什么PTC获胜 示例
大型代码库导航(>100个文件) PageRank对架构上重要的文件进行排名;代理无法读取所有文件 CB-5:Django ORM(2894个文件)
引用数据的论文研究 实时arxiv/引用计数的语义学者查询 PP-1,2,4:变压器/机器人调查
影响分析 静态依赖图+传递闭包 IM-1,2,4:爆炸半径估计
带有运行时数据的代码 树型解析,调用图构造 CB-1:延迟导入检测

PTC失去的地方:众所周知的API(pathlib、httpx)、稳定的知识域(异步模式、WASM)、模型训练数据完全覆盖的任何东西。

下一篇:复合查询

评估显示,PTC的代币成本来自 多次往返而不是工具本身。当前设计:

Agent → ptc_execute(build_graph)  → 3K result in context
Agent → ptc_execute(rank_files)   → 2K result in context
Agent → ptc_execute(extract_syms) → 2K result in context
Total: 3 calls, ~7K context tokens

重新设计将其压缩为:

Agent → ptc_execute(compound_code) → 400 token summary
Total: 1 call, ~400 context tokens

同样的计算发生在容器内部。只有结论回到了上下文。目标: 代币减少10-20倍 与用于探索任务的原生工具相比。

存储库结构

ptc-mcp/
├── server/                          # MCP server infrastructure
│   ├── server.py                    # FastMCP entry point (SSE transport)
│   ├── container_manager.py         # Docker lifecycle, REPL pool, IPC routing
│   ├── ipc_host.py                  # Host-side Unix socket server
│   ├── ipc_protocol.py              # Wire format (length-prefixed JSON)
│   ├── sandbox_runtime/             # Code running inside containers
│   ├── pulse_cleanup.py             # Orphaned container detection
│   ├── event_logger.py              # Structured event logging
│   ├── Dockerfile                   # Unified sandbox image
│   ├── ptc-daemon.sh                # Watchdog launcher
│   ├── tests/test_hardening.py      # Server unit tests
│   └── config.json                  # Resource limits, IPC config
│
├── ptc_tools/                       # Analysis library (runs inside containers)
│   ├── repomap.py                   # tree-sitter + PageRank codebase mapping
│   ├── symbols.py                   # Symbol extraction, API surface, diffing
│   ├── dependencies.py              # Call graphs, import cycles, change impact
│   ├── contracts.py                 # Env deps, shared state, side effects
│   ├── research/                    # Web search, papers, PDF, fetch pipelines
│   │   ├── papers.py                # arxiv + Semantic Scholar unified search
│   │   ├── search.py                # SearXNG / Tavily web search
│   │   ├── pipelines.py             # Extraction pipelines (sentences, entities)
│   │   └── ...                      # fetch, PDF, confidence, caching
│   ├── recipes/                     # 2-pass discover→extract patterns
│   ├── tests/                       # Unit tests with fixtures
│   └── benchmarks/                  # Evaluation suite
│       ├── harness.py               # Task definitions, judge builder, scoring
│       ├── agents/                  # System prompts (vanilla, tools, recipes, judge)
│       ├── tasks/                   # 25 task definitions across 5 domains
│       ├── ground_truth/            # Expected entities/facts per task
│       └── results/                 # All 100 agent outputs, judge verdicts, report
│           ├── final_report.json    # Aggregated scores, win rates, usage stats
│           ├── full_collected.json  # Raw agent outputs (1.5MB)
│           ├── per_task/            # Per-task combined outputs + verdicts
│           ├── prompts/             # All 75 agent prompts
│           └── judge_prompts/       # All 25 judge prompts
│
└── server/searxng/                  # Local search engine config

设置

# Start PTC server (requires Docker)
server/ptc-daemon.sh start

# Claude Code MCP config (one-time)
ln -s /path/to/ptc-mcp/server ~/.claude/mcp/ptc-server

# Verify
curl -s http://localhost:8741/sse --max-time 2

看 server/README.md 用于完整配置。

评估数据

所有基准工件都已提交并可复制:

工件 路径 大小
完整报告 ptc_tools/benchmarks/results/report.md 21KB
汇总结果 ptc_tools/benchmarks/results/final_report.json 100KB
原始试剂输出 ptc_tools/benchmarks/results/full_collected.json 1.5 MB
按任务细分 ptc_tools/benchmarks/results/per_task/ 25张图片
代理提示 ptc_tools/benchmarks/results/prompts/ 75张图片
法官提示 ptc_tools/benchmarks/results/judge_prompts/ 25张图片
地面真相 ptc_tools/benchmarks/ground_truth/ 25张图片
任务定义 ptc_tools/benchmarks/tasks/ 5个模块