当我把 Claude Code 从终端“搬“到服务器上之后...
本文分享了将Claude Code CLI工具改造成API服务的实践过程。作者通过分析Claude Code的内部机制,发现其核心是一个标准的tool_use循环,包括分块System Prompt、三层上下文压缩策略和独立子代理实例。基于这些发现,作者开发了CCServer项目,实现了多接口支持、项目级配置保留和多Agent编排功能。文章详细介绍了API调用方式、配置管理方案,以及实现过程中遇到
一个折腾的周末
上个月有个需求让我头疼了很久。
我们团队用 Claude Code 做内部工具开发,效率确实高——写 prompt、配几个 MCP 工具,一个功能半天就搭出来了。但问题也随之而来:这东西只能在终端用。
产品经理想把它集成到内部平台,让非技术的同事也能用;我想把几个常用的 Agent 封装成 API,供其他服务调用。但 Claude Code 是个 CLI 工具,强依赖终端交互,这要怎么搞?
那个周末我翻了好多资料,甚至考虑过用 expect 脚本模拟终端输入输出(别笑,真的试过),最后干脆心一横:要不自己研究一下它的内部机制,看能不能把核心能力抽出来?
摸索的过程
说干就干。我找了个开源项目 learn-claude-code,它通过拦截 Claude Code 发往 Anthropic API 的请求,分析出了 system prompt、工具定义、消息结构等参数。顺着这个思路,我搭了个简单的代理,开始观察 Claude Code 到底在干什么。
结果发现,Claude Code 的核心其实就是一个标准的 tool_use 循环,没有想象中那么神秘:
用户输入 → 构建消息 → 调 Anthropic API
↑___________________|
(循环直到结束)
几个关键发现:
System Prompt 是分块的 —— 不是一个大字符串,而是 content 块数组,分身份声明、工具说明、工作流、环境注入几段。环境注入那部分(当前时间、工作目录、CLAUDE.md 内容)是每轮动态追加的。
上下文压缩是三层策略 —— 日常对话微压缩(截断旧工具结果),超过阈值时触发 LLM 摘要,完整对话会存档到 transcripts 目录。这个机制保证了长对话不会爆 token。
子代理是独立实例 —— 通过特殊工具信号派生,有自己独立的 messages 列表和工具集,运行完把结果返回给父代理。嵌套深度有限制(默认 5 层)。
搞明白这些之后,我意识到:理论上完全可以复现这套机制,然后把 CLI 外壳换掉。
动手实现
接下来就是码代码的过程了。我给自己定了几个目标:
- 保持核心行为一致 —— 复现 Agent 循环、工具调用、子代理递归
- 支持多种接口 —— HTTP、SSE 流式、WebSocket 都要
- 保留 Claude Code 的项目级配置 —— .claude/ 那套东西很好用
- 支持多 Agent 编排 —— 复杂场景需要把多个 Agent 串起来
大概花了一周多时间,一个能跑通的版本出来了。给它起了个名字叫 CCServer(Claude Code Server 的缩写,虽然有点随意但好记)。
用起来怎么样
现在我的部署方式是:服务器上跑 CCServer,前端用 Gradio 做个简单界面,内部平台的其他服务直接调 HTTP 接口。
API 调用很简单:
# 创建会话
curl -X POST http://localhost:8000/sessions
# 直接对话(阻塞式)
curl -X POST http://localhost:8000/chat \
-H "X-Session-Id: xxx" \
-d '{"message": "分析这个目录的代码结构"}'
# 或者 SSE 流式
curl -X GET "http://localhost:8000/chat/stream?message=你好" \
-H "X-Session-Id: xxx"
配置管理还是熟悉的 .ccserver/ 目录:
.ccserver/
├── agents/ # 自定义 subagent
├── skills/ # 技能文档
├── hooks/ # 生命周期钩子
└── settings.json # 权限配置
格式和 Claude Code 的 .claude/ 保持一致,可以直接拷贝复用。
多 Agent 编排 是我觉得最有意思的部分。比如我做了个角色扮演对话系统,流程是这样的:
[用户输入] → [意图识别/搜索] → [话题建议] → [生成回复] → [质量检查]
↓___________|
(不通过则重试)
每个节点都是一个完整的 Claude Agent,节点间按 DAG 执行,支持条件回边做重试。这种显式编排比单 Agent 自主调度更可控,适合业务流程固定的场景。
一些踩坑记录
-
Prompt 兼容性 —— Claude Code 的 system prompt 结构在不同版本有变化,我实现了一个
PromptLib系统来管理不同版本的拼接逻辑,可以通过环境变量切换。 -
工具调用格式 —— 要严格按照 Anthropic API 的 tool_use / tool_result 格式来,参数类型也要对齐,否则模型行为会不一致。
-
会话隔离 —— 每个会话要有独立的工作目录沙箱,否则文件操作会互相干扰。我用
sessions/{session_id}/workdir/的方式来管理。 -
上下文压缩阈值 —— 默认 50000 字符触发 LLM 压缩,这个值要根据实际 token 消耗调整,不同模型的换算比例不一样。
写在最后
把 CCServer 部署到服务器之后,最大的感受是:Agent 能力终于可以用起来了。
以前写好的 prompt 和 MCP 配置,只能在终端里自己用。现在可以封装成接口,分享给团队,集成到各种流程里。对于一些复杂的多步骤场景,Graph 编排也让流程更清晰可控。
如果你也有类似需求——想把 Claude Code 的能力服务化、或者需要多 Agent 协作编排——可以试试看。项目已经开源(链接在文末),还在持续迭代中。
当然,这只是个学习研究性质的实现,不是官方项目,部分高级特性(比如 Claude Code 内置的那些专用 subagent)还没有完全对齐。但核心的 Agent 循环和工具系统已经挺稳定了,日常用下来没什么问题。
相关链接:
- 项目地址:https://github.com/kazeMace/ccserver
更多推荐


所有评论(0)