企业架构、智能体设计
开源JCR:用Jev树状路由解决agent上下文窗口优化
#AI智能体Agent
#GitHub工具库推荐
#Jev分类模型
2026-09-21
5K
banq
Niaz Morshed在2026年9月开源了JCR(Jev能力解析器),一刀把agent上下文窗口里塞满的冗余文档砍掉了85%!
开源JCR(Jev能力解析器)通过使用Jev树状路由解决了agent上下文窗口的冗余文档问题,将agent上下文窗口中的token数量从10万减少到1.5万。
--91likeyou---
塞满文档反而让agent变笨了
2026年的agent(智能体)开发圈有一个几乎没人质疑的共识:给agent喂越多文档,agent干活越靠谱。Claude Code的skills(技能文件)机制就是典型代表,开发者把Stripe的API手册、Slack的消息格式、Linear的工单模板全塞进.claude/skills目录,agent一开工就用Read、Glob、Grep三个文件系统命令把这些文件全部读进上下文窗口(context window)。上下文窗口就是agent的短期记忆工作台,所有指令、对话历史、参考资料都必须摊在这张桌子上agent才能看见,桌子面积有限,塞满了就放不下新东西。
但是Niaz Morshed在搭建自己的agent流水线时发现了一个诡异的现象:skills文件越多,agent的回答反而越跑偏,token(词元)账单还直线飙升。一个"创建Stripe客户然后发Slack通知"的两步任务,Claude Opus 5在skills模式下要吞掉108585个输入token,光输入成本就烧掉0.37美元。agent把大量脑容量花在了翻找"到底用哪个API端点"这件破事上,真正用来推理和执行的token所剩无几!
这就怪了,说明书越多agent反而越找不到重点?问题出在上下文窗口本身就是一个固定容量的工作台,你把整本百科全书摊在桌面上,agent光是翻目录就累瘫了,哪还有精力干活!
11360条命令塞不进上下文窗口
Niaz Morshed把市面上主流SaaS平台的API文档全部拆解成了标准化的JSON条目,最终攒出了一个包含11个顶级分组、960个节点、11360条具体命令的能力目录(capability catalog)。能力目录覆盖了Git、Stripe、Slack、Linear、Railway等开发者日常打交道的几乎所有服务,每条命令都附带了完整的endpoint、参数、前置条件和返回值说明,最大节点深度达到六层,单个节点下最多挂了175个子项。
传统RAG(检索增强生成)的做法是把这11360条命令全部向量化,扔进一个向量数据库,agent提问时用embedding做相似度匹配,LangChain和LlamaIndex这类框架走的就是这条路。向量搜索听起来很聪明,但实际效果经常翻车:当用户说"创建一个客户"时,向量数据库会把Stripe的创建客户、HubSpot的创建、Salesforce的创建Lead全部返回,因为这三个操作的语义向量几乎重叠,agent拿到一堆似是而非的结果还得自己判断哪个对,上下文窗口又被垃圾信息塞满了!
Niaz Morshed选择了一条完全不同的路:把11360条命令组织成一棵六层深的目录树,让Jev路由模型在每一层只做一道选择题。比如第一层问"这个任务跟支付有关还是跟通讯有关",第二层问"是Stripe还是PayPal",第三层问"是创建客户还是退款",一路缩窄到具体的命令条目。JCR的树状路由跟RAG的向量搜索最大的区别就在这里:Jev每次只在当前节点的子目录里做选择,搜索空间从11360瞬间缩小到十几甚至几个选项,agent上下文窗口里只出现最终命中的那几条命令的context字段!
Jev路由模型逐层做选择题
Jev是Typesafe公司开发的一种专门做分类和路由的小模型,速度极快,成本极低。JCR把Jev当作一个"目录导航员"来用:当agent发来"创建Stripe客户然后发Slack通知"这个请求时,JCR的第一步是让Jev判断这个请求是单步操作还是复合操作。Jev判定为复合操作后,JCR调用OpenAI的gpt-5.6-luna把请求拆成两个子任务:"创建Stripe客户"和"在Slack频道发送客户链接",单步请求则直接跳过拆分环节。
拆分完成后,JCR对两个子任务并行启动树状搜索。以"创建Stripe客户"为例,Jev站在能力目录的根节点,面前摆着git、stripe、slack、linear等11个一级分组,Jev根据每个分组的name和description字段打分,stripe分组的描述"Process payments, manage customers, and handle subscriptions"跟"创建客户"高度匹配,Jev直接选中stripe分支。整个过程Jev只看了11个选项,而不是11360个!
进入stripe节点后,Jev面前出现了customers、charges、refunds、invoices等子分组,Jev再次打分选中customers。再往下走一层,Jev在create-customer、list-customers、update-customer、delete-customer四个具体命令里选中create-customer。从根节点到叶子节点,Jev总共只做了三道选择题,每道题的选项不超过20个,agent上下文窗口自始至终没有看到其他11356条命令的任何信息。JCR给每步搜索设了16轮路由预算,超过16轮还没找到结果就返回depth-limit(深度限制)提示,让agent自行收窄请求。
束搜索砍掉死胡同路径
但是现实中的目录树不会这么干净利落。有时候Jev在某一层的打分非常接近,比如"创建客户"这个请求在stripe/customers和hubspot/contacts两个分支上的得分几乎一样高,如果JCR只保留得分最高的那一条路径,一旦选错就彻底走进死胡同,agent拿到的context完全是错的。
JCR的解决办法是束搜索(beam search):在每一层保留得分最高的前三条路径,前提是这些路径的得分不低于最佳路径的60%。JCR用几何平均数来计算每条路径的累积得分,而不是简单相加,这样可以防止某一层的高分掩盖另一层的低分。当三条路径同时往下探索时,JCR会在后续的层级里逐步淘汰得分掉队的分支,最终只把存活下来的路径对应的context返回给agent。
Niaz Morshed把束搜索的宽度默认设为3,带宽比设为0.6,这两个参数可以通过环境变量JCR_BEAM_WIDTH和JCR_BAND_RATIO调整。束搜索宽度越大,JCR探索的候选路径越多,agent拿到正确结果的概率越高,但Jev路由模型的调用次数也会成倍增加,整体延迟和成本随之上升。Niaz Morshed在README里明确警告:更宽的束搜索意味着更多的路由工作量,开发者需要在准确率和成本之间自己找平衡点!
Opus 5实测token暴跌85%
Niaz Morshed设计了20个真实场景的benchmark(基准测试),涵盖支付、通讯、项目管理、部署等常见任务,用Claude Opus 5和GPT-5.6-Sol两个agent分别跑skills模式和JCR模式,总共完成了80次完整运行。所有运行只让agent查找指令并解释步骤,没有真正执行API调用,因此对比的是纯粹的信息检索效率。
Claude Opus 5的数据最炸裂:skills模式下agent平均吞掉108585个输入token,切换到JCR模式后骤降到15819个token,降幅高达85%!总成本从0.37美元降到0.12美元,省了67%。JCR模式下的agent上下文窗口里只出现了resolve_capabilities返回的几条精确命令,而不是skills模式下被Read、Glob、Grep三个文件系统命令反复拉进来的整页整页的markdown文档。
GPT-5.6-Sol的降幅没那么夸张,但也有23%:输入token从61952降到47669,成本从0.1377美元降到0.1151美元,省了16%。Sol本身在skills模式下的token消耗就比Opus 5低得多,说明不同agent对上下文窗口的利用效率差异巨大,JCR带来的收益跟agent本身的阅读习惯强相关!
Sol跑JCR反而慢了2.5倍
但是token省了不代表速度也快了。GPT-5.6-Sol在JCR模式下的平均墙钟时间从25.3秒暴涨到62.4秒,慢了将近2.5倍!Niaz Morshed在benchmark报告里坦承,有一次Sol的JCR运行甚至飙到了372.6秒,单次运行里JCR被调用了两次,Jev路由模型被调用了193次,直接把平均值拉飞了。
这个结果其实不难理解:skills模式下agent直接读本地文件,磁盘IO几乎零延迟;JCR模式下agent要先调用resolve_capabilities命令,JCR内部再调Jev做分类、调OpenAI做拆分、再调Jev做多轮树状搜索,整个链路的网络延迟叠加起来远比读几个本地文件慢。Niaz Morshed在README里也承认,20个场景中有19个场景Sol跑JCR比跑skills更慢,那个372秒的极端值只能解释一部分差距!
这就形成了一个非常有趣的取舍:JCR用时间换空间,用更长的等待换来了更小的上下文窗口和更低的token账单。对于Opus 5这种按token计费极贵的大模型,省85%的token绝对值得多等几十秒;但对于Sol这种本身就便宜且快速的模型,JCR带来的成本节省只有16%,却要付出2.5倍的时间代价,到底划不划算完全取决于你的具体场景和预算约束。
你的agent该不该换搜索方式
Niaz Morshed在JCR的README里反复强调一个边界:JCR只返回文档,不执行任何命令。agent拿到resolve_capabilities返回的context文本后,怎么填参数、怎么管理凭证、怎么处理步骤间的依赖关系,全部由agent自己的执行逻辑负责。JCR把自己严格限定在"查说明书"这个单一职责上,跟LangChain那种把检索和执行耦合在一起的RAG管线形成了鲜明对比。
如果你想在自己的agent里试用JCR,最快的方式是启动JCR内置的MCP(Model Context Protocol,模型上下文协议)服务器。Niaz Morshed把JCR封装成了一个标准的stdio MCP服务,任何支持MCP协议的agent框架都可以直接调用resolve_capabilities命令,启动命令只需要一行:
CAPABILITIES_DIRECTORY="$PWD/capabilities" \
node --env-file=.env --import tsx src/jcr/server.ts
但是Niaz Morshed的benchmark数据留下了一个至今没有解释清楚的矛盾:同一个JCR在同一套20个场景上,让Opus 5的墙钟时间从105.5秒缩短到77.7秒,却让Sol的墙钟时间从25.3秒暴涨到62.4秒,一个变快一个变慢,方向完全相反,而Niaz Morshed在README里只给了一句"重复运行会有助于分离解析器延迟和API波动"的模糊解释,至今没有公布第二次运行的对比数据。
🔥 热词:#开源JCR · #用Jev树状路由解决agent上下文窗口优化 · #企业架构、智能体设计 · #AI智能体Agent · #GitHub工具库推荐 · #Jev分类模型